From 9d8609dd08c0992a321c5793c5b4b307e7e439a8 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 26 Nov 2019 10:25:50 +0000 Subject: [PATCH 001/119] Modify and snap to circle in user coordinates Correct modify interaction at center and at drawn circle circumference Correct snap interaction at drawn circle circumference Test circle geometry in a user projection --- src/ol/interaction/Modify.js | 47 +++++++-- src/ol/interaction/Snap.js | 22 +++- test/spec/ol/interaction/modify.test.js | 128 +++++++++++++++++++++++- test/spec/ol/interaction/snap.test.js | 27 ++++- 4 files changed, 210 insertions(+), 14 deletions(-) diff --git a/src/ol/interaction/Modify.js b/src/ol/interaction/Modify.js index fe81a771ee..dffdf8e707 100644 --- a/src/ol/interaction/Modify.js +++ b/src/ol/interaction/Modify.js @@ -14,13 +14,14 @@ import {always, primaryAction, altKeyOnly, singleClick} from '../events/conditio import {boundingExtent, buffer as bufferExtent, createOrUpdateFromCoordinate as createExtent} from '../extent.js'; import GeometryType from '../geom/GeometryType.js'; import Point from '../geom/Point.js'; +import {fromCircle} from '../geom/Polygon.js'; import PointerInteraction from './Pointer.js'; import VectorLayer from '../layer/Vector.js'; import VectorSource from '../source/Vector.js'; import VectorEventType from '../source/VectorEventType.js'; import RBush from '../structs/RBush.js'; import {createEditingStyle} from '../style/Style.js'; -import {fromUserExtent, toUserExtent, fromUserCoordinate, toUserCoordinate} from '../proj.js'; +import {getUserProjection, fromUserExtent, toUserExtent, fromUserCoordinate, toUserCoordinate} from '../proj.js'; /** @@ -657,7 +658,14 @@ class Modify extends PointerInteraction { centerSegmentData.featureSegments = featureSegments; circumferenceSegmentData.featureSegments = featureSegments; this.rBush_.insert(createExtent(coordinates), centerSegmentData); - this.rBush_.insert(geometry.getExtent(), circumferenceSegmentData); + let circleGeometry = /** @type {import("../geom/Geometry.js").default} */ (geometry); + const userProjection = getUserProjection(); + if (userProjection && this.getMap()) { + const projection = this.getMap().getView().getProjection(); + circleGeometry = circleGeometry.clone().transform(userProjection, projection); + circleGeometry = fromCircle(/** @type {import("../geom/Circle.js").default} */ (circleGeometry)).transform(projection, userProjection); + } + this.rBush_.insert(circleGeometry.getExtent(), circumferenceSegmentData); } /** @@ -785,7 +793,16 @@ class Modify extends PointerInteraction { this.changingFeature_ = false; } else { // We're dragging the circle's circumference: this.changingFeature_ = true; - geometry.setRadius(coordinateDistance(geometry.getCenter(), vertex)); + const projection = evt.map.getView().getProjection(); + let radius = coordinateDistance(fromUserCoordinate(geometry.getCenter(), projection), + fromUserCoordinate(vertex, projection)); + const userProjection = getUserProjection(); + if (userProjection) { + const circleGeometry = geometry.clone().transform(userProjection, projection); + circleGeometry.setRadius(radius); + radius = circleGeometry.transform(projection, userProjection).getRadius(); + } + geometry.setRadius(radius); this.changingFeature_ = false; } break; @@ -898,7 +915,14 @@ class Modify extends PointerInteraction { circumferenceSegmentData.segment[0] = coordinates; circumferenceSegmentData.segment[1] = coordinates; this.rBush_.update(createExtent(coordinates), centerSegmentData); - this.rBush_.update(geometry.getExtent(), circumferenceSegmentData); + let circleGeometry = geometry; + const userProjection = getUserProjection(); + if (userProjection) { + const projection = evt.map.getView().getProjection(); + circleGeometry = circleGeometry.clone().transform(userProjection, projection); + circleGeometry = fromCircle(circleGeometry).transform(projection, userProjection); + } + this.rBush_.update(circleGeometry.getExtent(), circumferenceSegmentData); } else { this.rBush_.update(boundingExtent(segmentData.segment), segmentData); } @@ -1249,11 +1273,15 @@ function projectedDistanceToSegmentDataSquared(pointCoordinates, segmentData, pr const geometry = segmentData.geometry; if (geometry.getType() === GeometryType.CIRCLE) { - const circleGeometry = /** @type {import("../geom/Circle.js").default} */ (geometry); + let circleGeometry = /** @type {import("../geom/Circle.js").default} */ (geometry); if (segmentData.index === CIRCLE_CIRCUMFERENCE_INDEX) { + const userProjection = getUserProjection(); + if (userProjection) { + circleGeometry = /** @type {import("../geom/Circle.js").default} */ (circleGeometry.clone().transform(userProjection, projection)); + } const distanceToCenterSquared = - squaredCoordinateDistance(circleGeometry.getCenter(), pointCoordinates); + squaredCoordinateDistance(circleGeometry.getCenter(), fromUserCoordinate(pointCoordinates, projection)); const distanceToCircumference = Math.sqrt(distanceToCenterSquared) - circleGeometry.getRadius(); return distanceToCircumference * distanceToCircumference; @@ -1280,7 +1308,12 @@ function closestOnSegmentData(pointCoordinates, segmentData, projection) { const geometry = segmentData.geometry; if (geometry.getType() === GeometryType.CIRCLE && segmentData.index === CIRCLE_CIRCUMFERENCE_INDEX) { - return geometry.getClosestPoint(pointCoordinates); + let circleGeometry = /** @type {import("../geom/Circle.js").default} */ (geometry); + const userProjection = getUserProjection(); + if (userProjection) { + circleGeometry = /** @type {import("../geom/Circle.js").default} */ (circleGeometry.clone().transform(userProjection, projection)); + } + return toUserCoordinate(circleGeometry.getClosestPoint(fromUserCoordinate(pointCoordinates, projection)), projection); } const coordinate = fromUserCoordinate(pointCoordinates, projection); tempSegment[0] = fromUserCoordinate(segmentData.segment[0], projection); diff --git a/src/ol/interaction/Snap.js b/src/ol/interaction/Snap.js index 8cf720768a..61a5a1c6de 100644 --- a/src/ol/interaction/Snap.js +++ b/src/ol/interaction/Snap.js @@ -14,7 +14,7 @@ import PointerInteraction from './Pointer.js'; import {getValues} from '../obj.js'; import VectorEventType from '../source/VectorEventType.js'; import RBush from '../structs/RBush.js'; -import {fromUserCoordinate, toUserCoordinate} from '../proj.js'; +import {getUserProjection, fromUserCoordinate, toUserCoordinate} from '../proj.js'; /** @@ -431,8 +431,13 @@ class Snap extends PointerInteraction { } else if (this.edge_) { const isCircle = closestSegmentData.feature.getGeometry().getType() === GeometryType.CIRCLE; if (isCircle) { - vertex = closestOnCircle(pixelCoordinate, - /** @type {import("../geom/Circle.js").default} */ (closestSegmentData.feature.getGeometry())); + let circleGeometry = closestSegmentData.feature.getGeometry(); + const userProjection = getUserProjection(); + if (userProjection) { + circleGeometry = circleGeometry.clone().transform(userProjection, projection); + } + vertex = toUserCoordinate(closestOnCircle(projectedCoordinate, + /** @type {import("../geom/Circle.js").default} */ (circleGeometry)), projection); } else { tempSegment[0] = fromUserCoordinate(closestSegment[0], projection); tempSegment[1] = fromUserCoordinate(closestSegment[1], projection); @@ -482,7 +487,16 @@ class Snap extends PointerInteraction { * @private */ writeCircleGeometry_(feature, geometry) { - const polygon = fromCircle(geometry); + const projection = this.getMap().getView().getProjection(); + let circleGeometry = geometry; + const userProjection = getUserProjection(); + if (userProjection) { + circleGeometry = /** @type {import("../geom/Circle.js").default} */ (circleGeometry.clone().transform(userProjection, projection)); + } + const polygon = fromCircle(circleGeometry); + if (userProjection) { + polygon.transform(projection, userProjection); + } const coordinates = polygon.getCoordinates()[0]; for (let i = 0, ii = coordinates.length - 1; i < ii; ++i) { const segment = coordinates.slice(i, i + 2); diff --git a/test/spec/ol/interaction/modify.test.js b/test/spec/ol/interaction/modify.test.js index 7deae8d5d7..d8b8cccfb0 100644 --- a/test/spec/ol/interaction/modify.test.js +++ b/test/spec/ol/interaction/modify.test.js @@ -14,6 +14,7 @@ import VectorLayer from '../../../../src/ol/layer/Vector.js'; import VectorSource from '../../../../src/ol/source/Vector.js'; import Event from '../../../../src/ol/events/Event.js'; import {getValues} from '../../../../src/ol/obj.js'; +import {clearUserProjection, setUserProjection} from '../../../../src/ol/proj.js'; describe('ol.interaction.Modify', function() { @@ -66,6 +67,7 @@ describe('ol.interaction.Modify', function() { afterEach(function() { map.dispose(); document.body.removeChild(target); + clearUserProjection(); }); /** @@ -401,7 +403,7 @@ describe('ol.interaction.Modify', function() { expect(circleFeature.getGeometry().getRadius()).to.equal(20); expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); - // Increase radius + // Increase radius along x axis simulateEvent('pointermove', 25, -4, null, 0); simulateEvent('pointerdown', 25, -4, null, 0); simulateEvent('pointermove', 30, -5, null, 0); @@ -410,6 +412,64 @@ describe('ol.interaction.Modify', function() { expect(circleFeature.getGeometry().getRadius()).to.equal(25); expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); + + // Increase radius along y axis + simulateEvent('pointermove', 4, -30, null, 0); + simulateEvent('pointerdown', 4, -30, null, 0); + simulateEvent('pointermove', 5, -35, null, 0); + simulateEvent('pointerdrag', 5, -35, null, 0); + simulateEvent('pointerup', 5, -35, null, 0); + + expect(circleFeature.getGeometry().getRadius()).to.equal(30); + expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); + }); + + it('changes the circle radius and center in a user projection', function() { + const userProjection = 'EPSG:3857'; + setUserProjection(userProjection); + const viewProjection = map.getView().getProjection(); + + const circleFeature = new Feature(new Circle([10, 10], 20).transform(viewProjection, userProjection)); + features.length = 0; + features.push(circleFeature); + + const modify = new Modify({ + features: new Collection(features) + }); + map.addInteraction(modify); + + // Change center + simulateEvent('pointermove', 10, -10, null, 0); + simulateEvent('pointerdown', 10, -10, null, 0); + simulateEvent('pointermove', 5, -5, null, 0); + simulateEvent('pointerdrag', 5, -5, null, 0); + simulateEvent('pointerup', 5, -5, null, 0); + + const geometry1 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry1.getRadius()).to.roughlyEqual(20, 1e-9); + expect(geometry1.getCenter()).to.eql([5, 5]); + + // Increase radius along x axis + simulateEvent('pointermove', 25, -4, null, 0); + simulateEvent('pointerdown', 25, -4, null, 0); + simulateEvent('pointermove', 30, -5, null, 0); + simulateEvent('pointerdrag', 30, -5, null, 0); + simulateEvent('pointerup', 30, -5, null, 0); + + const geometry2 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry2.getRadius()).to.roughlyEqual(25, 1e-9); + expect(geometry2.getCenter()).to.eql([5, 5]); + + // Increase radius along y axis + simulateEvent('pointermove', 4, -30, null, 0); + simulateEvent('pointerdown', 4, -30, null, 0); + simulateEvent('pointermove', 5, -35, null, 0); + simulateEvent('pointerdrag', 5, -35, null, 0); + simulateEvent('pointerup', 5, -35, null, 0); + + const geometry3 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry3.getRadius()).to.roughlyEqual(30, 1e-9); + expect(geometry3.getCenter()).to.eql([5, 5]); }); }); @@ -765,7 +825,7 @@ describe('ol.interaction.Modify', function() { expect(circleFeature.getGeometry().getRadius()).to.equal(20); expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); - // Increase radius + // Increase radius along x axis simulateEvent('pointermove', 25, -4, null, 0); simulateEvent('pointerdown', 25, -4, null, 0); simulateEvent('pointermove', 30, -5, null, 0); @@ -774,6 +834,70 @@ describe('ol.interaction.Modify', function() { expect(circleFeature.getGeometry().getRadius()).to.equal(25); expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); + + // Increase radius along y axis + simulateEvent('pointermove', 4, -30, null, 0); + simulateEvent('pointerdown', 4, -30, null, 0); + simulateEvent('pointermove', 5, -35, null, 0); + simulateEvent('pointerdrag', 5, -35, null, 0); + simulateEvent('pointerup', 5, -35, null, 0); + + expect(circleFeature.getGeometry().getRadius()).to.equal(30); + expect(circleFeature.getGeometry().getCenter()).to.eql([5, 5]); + }); + + it('changes the circle radius and center in a user projection', function() { + const userProjection = 'EPSG:3857'; + setUserProjection(userProjection); + const viewProjection = map.getView().getProjection(); + + const circleFeature = new Feature(new Circle([10, 10], 20).transform(viewProjection, userProjection)); + features.length = 0; + features.push(circleFeature); + + const modify = new Modify({ + features: new Collection(features) + }); + map.addInteraction(modify); + + const snap = new Snap({ + features: new Collection(features), + pixelTolerance: 1 + }); + map.addInteraction(snap); + + // Change center + simulateEvent('pointermove', 10, -10, null, 0); + simulateEvent('pointerdown', 10, -10, null, 0); + simulateEvent('pointermove', 5, -5, null, 0); + simulateEvent('pointerdrag', 5, -5, null, 0); + simulateEvent('pointerup', 5, -5, null, 0); + + const geometry1 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry1.getRadius()).to.roughlyEqual(20, 1e-9); + expect(geometry1.getCenter()).to.eql([5, 5]); + + // Increase radius along x axis + simulateEvent('pointermove', 25, -4, null, 0); + simulateEvent('pointerdown', 25, -4, null, 0); + simulateEvent('pointermove', 30, -5, null, 0); + simulateEvent('pointerdrag', 30, -5, null, 0); + simulateEvent('pointerup', 30, -5, null, 0); + + const geometry2 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry2.getRadius()).to.roughlyEqual(25, 1e-9); + expect(geometry2.getCenter()).to.eql([5, 5]); + + // Increase radius along y axis + simulateEvent('pointermove', 4, -30, null, 0); + simulateEvent('pointerdown', 4, -30, null, 0); + simulateEvent('pointermove', 5, -35, null, 0); + simulateEvent('pointerdrag', 5, -35, null, 0); + simulateEvent('pointerup', 5, -35, null, 0); + + const geometry3 = circleFeature.getGeometry().clone().transform(userProjection, viewProjection); + expect(geometry3.getRadius()).to.roughlyEqual(30, 1e-9); + expect(geometry3.getCenter()).to.eql([5, 5]); }); }); diff --git a/test/spec/ol/interaction/snap.test.js b/test/spec/ol/interaction/snap.test.js index 329cd08172..7db59f177b 100644 --- a/test/spec/ol/interaction/snap.test.js +++ b/test/spec/ol/interaction/snap.test.js @@ -6,7 +6,7 @@ import Circle from '../../../../src/ol/geom/Circle.js'; import Point from '../../../../src/ol/geom/Point.js'; import LineString from '../../../../src/ol/geom/LineString.js'; import Snap from '../../../../src/ol/interaction/Snap.js'; -import {useGeographic, clearUserProjection} from '../../../../src/ol/proj.js'; +import {useGeographic, clearUserProjection, setUserProjection, transform} from '../../../../src/ol/proj.js'; import {overrideRAF} from '../../util.js'; @@ -55,6 +55,7 @@ describe('ol.interaction.Snap', function() { afterEach(function() { map.dispose(); document.body.removeChild(target); + clearUserProjection(); }); it('can handle XYZ coordinates', function() { @@ -129,6 +130,30 @@ describe('ol.interaction.Snap', function() { expect(event.coordinate[1]).to.roughlyEqual(Math.sin(Math.PI / 4) * 10, 1e-10); }); + it('snaps to circle in a user projection', function() { + const userProjection = 'EPSG:3857'; + setUserProjection(userProjection); + const viewProjection = map.getView().getProjection(); + + const circle = new Feature(new Circle([0, 0], 10).transform(viewProjection, userProjection)); + const snapInteraction = new Snap({ + features: new Collection([circle]), + pixelTolerance: 5 + }); + snapInteraction.setMap(map); + + const event = { + pixel: [5 + width / 2, height / 2 - 5], + coordinate: transform([5, 5], viewProjection, userProjection), + map: map + }; + snapInteraction.handleEvent(event); + + const coordinate = transform([Math.sin(Math.PI / 4) * 10, Math.sin(Math.PI / 4) * 10], viewProjection, userProjection); + expect(event.coordinate[0]).to.roughlyEqual(coordinate[0], 1e-10); + expect(event.coordinate[1]).to.roughlyEqual(coordinate[1], 1e-10); + }); + it('handle feature without geometry', function() { const feature = new Feature(); const snapInteraction = new Snap({ From 5b1df4438d89c18d162d775f0fdca91f6c782043 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Wed, 1 Jan 2020 22:04:10 +0000 Subject: [PATCH 002/119] Fix for undefined source in Image layer Prevent error if layer does not have a source. Also clear any existing image if source is set to null or undefined by setSource. --- src/ol/renderer/canvas/ImageLayer.js | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/src/ol/renderer/canvas/ImageLayer.js b/src/ol/renderer/canvas/ImageLayer.js index 5dc9895cd0..7403890219 100644 --- a/src/ol/renderer/canvas/ImageLayer.js +++ b/src/ol/renderer/canvas/ImageLayer.js @@ -55,16 +55,20 @@ class CanvasImageLayerRenderer extends CanvasLayerRenderer { } if (!hints[ViewHint.ANIMATING] && !hints[ViewHint.INTERACTING] && !isEmpty(renderedExtent)) { - let projection = viewState.projection; - if (!ENABLE_RASTER_REPROJECTION) { - const sourceProjection = imageSource.getProjection(); - if (sourceProjection) { - projection = sourceProjection; + if (imageSource) { + let projection = viewState.projection; + if (!ENABLE_RASTER_REPROJECTION) { + const sourceProjection = imageSource.getProjection(); + if (sourceProjection) { + projection = sourceProjection; + } } - } - const image = imageSource.getImage(renderedExtent, viewResolution, pixelRatio, projection); - if (image && this.loadImage(image)) { - this.image_ = image; + const image = imageSource.getImage(renderedExtent, viewResolution, pixelRatio, projection); + if (image && this.loadImage(image)) { + this.image_ = image; + } + } else { + this.image_ = null; } } From d2b05991772342cf1c9afbc8c6584f6b853a5223 Mon Sep 17 00:00:00 2001 From: philip Date: Tue, 14 Jan 2020 13:39:52 +0000 Subject: [PATCH 003/119] Dynamically chose the number of subdivisions based on the size of the Image. --- src/ol/reproj/Image.js | 2 +- src/ol/reproj/Tile.js | 2 +- src/ol/reproj/Triangulation.js | 11 ++++++++--- 3 files changed, 10 insertions(+), 5 deletions(-) diff --git a/src/ol/reproj/Image.js b/src/ol/reproj/Image.js index e08778002c..7a5cfd7240 100644 --- a/src/ol/reproj/Image.js +++ b/src/ol/reproj/Image.js @@ -47,7 +47,7 @@ class ReprojImage extends ImageBase { const triangulation = new Triangulation( sourceProj, targetProj, limitedTargetExtent, maxSourceExtent, - sourceResolution * errorThresholdInPixels); + sourceResolution * errorThresholdInPixels, targetResolution); const sourceExtent = triangulation.calculateSourceExtent(); const sourceImage = getImageFunction(sourceExtent, sourceResolution, pixelRatio); diff --git a/src/ol/reproj/Tile.js b/src/ol/reproj/Tile.js index 73d508d203..7defc9e48b 100644 --- a/src/ol/reproj/Tile.js +++ b/src/ol/reproj/Tile.js @@ -160,7 +160,7 @@ class ReprojTile extends Tile { */ this.triangulation_ = new Triangulation( sourceProj, targetProj, limitedTargetExtent, maxSourceExtent, - sourceResolution * errorThresholdInPixels); + sourceResolution * errorThresholdInPixels, targetResolution); if (this.triangulation_.getTriangles().length === 0) { // no valid triangles -> EMPTY diff --git a/src/ol/reproj/Triangulation.js b/src/ol/reproj/Triangulation.js index ebdab668da..fc75ce7a9c 100644 --- a/src/ol/reproj/Triangulation.js +++ b/src/ol/reproj/Triangulation.js @@ -1,7 +1,7 @@ /** * @module ol/reproj/Triangulation */ -import {boundingExtent, createEmpty, extendCoordinate, getBottomLeft, getBottomRight, +import {boundingExtent, createEmpty, extendCoordinate, getArea, getBottomLeft, getBottomRight, getTopLeft, getTopRight, getWidth, intersects} from '../extent.js'; import {modulo} from '../math.js'; import {getTransform} from '../proj.js'; @@ -49,8 +49,9 @@ class Triangulation { * @param {import("../extent.js").Extent} targetExtent Target extent to triangulate. * @param {import("../extent.js").Extent} maxSourceExtent Maximal source extent that can be used. * @param {number} errorThreshold Acceptable error (in source units). + * @param {number} destinationResolution The (optional) resolution of the destination. */ - constructor(sourceProj, targetProj, targetExtent, maxSourceExtent, errorThreshold) { + constructor(sourceProj, targetProj, targetExtent, maxSourceExtent, errorThreshold, destinationResolution) { /** * @type {import("../proj/Projection.js").default} @@ -138,11 +139,15 @@ class Triangulation { const sourceBottomRight = this.transformInv_(destinationBottomRight); const sourceBottomLeft = this.transformInv_(destinationBottomLeft); + const maxSubdivision = MAX_SUBDIVISION + (destinationResolution ? + Math.max(0, Math.ceil(Math.log2(getArea(targetExtent) / (destinationResolution * destinationResolution * 256 * 256)))) + : 0); + this.addQuad_( destinationTopLeft, destinationTopRight, destinationBottomRight, destinationBottomLeft, sourceTopLeft, sourceTopRight, sourceBottomRight, sourceBottomLeft, - MAX_SUBDIVISION); + maxSubdivision); if (this.wrapsXInSource_) { let leftBound = Infinity; From ccf3532eb2d4a42e818930dc44e63091dfd369e4 Mon Sep 17 00:00:00 2001 From: philip Date: Tue, 14 Jan 2020 13:48:23 +0000 Subject: [PATCH 004/119] Fix the parameter name to have the opt_ prefix. --- src/ol/reproj/Triangulation.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/ol/reproj/Triangulation.js b/src/ol/reproj/Triangulation.js index fc75ce7a9c..b6091d149f 100644 --- a/src/ol/reproj/Triangulation.js +++ b/src/ol/reproj/Triangulation.js @@ -49,9 +49,9 @@ class Triangulation { * @param {import("../extent.js").Extent} targetExtent Target extent to triangulate. * @param {import("../extent.js").Extent} maxSourceExtent Maximal source extent that can be used. * @param {number} errorThreshold Acceptable error (in source units). - * @param {number} destinationResolution The (optional) resolution of the destination. + * @param {?number} opt_destinationResolution The (optional) resolution of the destination. */ - constructor(sourceProj, targetProj, targetExtent, maxSourceExtent, errorThreshold, destinationResolution) { + constructor(sourceProj, targetProj, targetExtent, maxSourceExtent, errorThreshold, opt_destinationResolution) { /** * @type {import("../proj/Projection.js").default} @@ -139,8 +139,9 @@ class Triangulation { const sourceBottomRight = this.transformInv_(destinationBottomRight); const sourceBottomLeft = this.transformInv_(destinationBottomLeft); - const maxSubdivision = MAX_SUBDIVISION + (destinationResolution ? - Math.max(0, Math.ceil(Math.log2(getArea(targetExtent) / (destinationResolution * destinationResolution * 256 * 256)))) + const maxSubdivision = MAX_SUBDIVISION + (opt_destinationResolution ? + Math.max(0, Math.ceil(Math.log2(getArea(targetExtent) / + (opt_destinationResolution * opt_destinationResolution * 256 * 256)))) : 0); this.addQuad_( From 0057144b52e285c8dbaae5a28896cb6298c74e30 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Fri, 7 Feb 2020 00:24:56 +0100 Subject: [PATCH 005/119] Add apidoc-debug task to debug the apidoc generation process --- package.json | 1 + 1 file changed, 1 insertion(+) diff --git a/package.json b/package.json index 5c5dad91a3..a99e2855af 100644 --- a/package.json +++ b/package.json @@ -24,6 +24,7 @@ "copy-css": "shx cp src/ol/ol.css build/ol/ol.css", "transpile": "shx rm -rf build/ol && shx mkdir -p build/ol && shx cp -rf src/ol build/ol/src && node tasks/serialize-workers && tsc --project config/tsconfig-build.json", "typecheck": "tsc --pretty", + "apidoc-debug": "shx rm -rf build/apidoc && node --inspect-brk=9229 ./node_modules/jsdoc/jsdoc.js -R config/jsdoc/api/index.md -c config/jsdoc/api/conf.json -P package.json -d build/apidoc", "apidoc": "shx rm -rf build/apidoc && jsdoc -R config/jsdoc/api/index.md -c config/jsdoc/api/conf.json -P package.json -d build/apidoc" }, "main": "index.js", From 7a77793d697fa5c8c07497cd1b9c78f20655bb45 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 11 Feb 2020 14:58:57 +0000 Subject: [PATCH 006/119] Write fill and outline in PolyStyle Write styles based on style objects appropriate for geometry. Write fill and outline in PolyStyle if false (i.e. non-default) Handle MultiLineString, MultiPoint and MultiPolygon within heterogenous MultiGeometry when writing features Add getGeometriesArrayRecursive method to ol/geom/GeometryCollection to allow for nested MultiGeometry Enhanced write GeometryCollection geometries test A more rigorous write GeometryCollection geometries test including nested collections (the output is simplified to a single MultiGeomtry) Add writeFeatures to outline and fill tests, setting geometry for geometry specific tests Add 0 and 0 to some existing tests --- src/ol/format/KML.js | 173 ++++++++++++++++++------- src/ol/geom/GeometryCollection.js | 17 +++ test/spec/ol/format/kml.test.js | 205 +++++++++++++++++++++++++++++- 3 files changed, 344 insertions(+), 51 deletions(-) diff --git a/src/ol/format/KML.js b/src/ol/format/KML.js index d94a4c473b..68506c466e 100644 --- a/src/ol/format/KML.js +++ b/src/ol/format/KML.js @@ -918,11 +918,7 @@ function createNameStyleFunction(foundStyle, name) { const nameStyle = new Style({ image: imageStyle, - text: textStyle, - // although nameStyle will be used only for Point geometries - // fill and stroke are included to assist writing of MultiGeometry styles - fill: foundStyle.getFill(), - stroke: foundStyle.getStroke() + text: textStyle }); return nameStyle; } @@ -953,7 +949,7 @@ function createFeatureStyleFunction(style, styleUrl, defaultStyle, sharedStyles, if (geometry) { const type = geometry.getType(); if (type === GeometryType.GEOMETRY_COLLECTION) { - multiGeometryPoints = geometry.getGeometriesArray().filter(function(geometry) { + multiGeometryPoints = geometry.getGeometriesArrayRecursive().filter(function(geometry) { const type = geometry.getType(); return type === GeometryType.POINT || type === GeometryType.MULTI_POINT; }); @@ -1806,7 +1802,7 @@ function readStyle(node, objectStack) { const type = geometry.getType(); if (type === GeometryType.GEOMETRY_COLLECTION) { return new GeometryCollection( - geometry.getGeometriesArray().filter(function(geometry) { + geometry.getGeometriesArrayRecursive().filter(function(geometry) { const type = geometry.getType(); return type !== GeometryType.POLYGON && type !== GeometryType.MULTI_POLYGON; }) @@ -1827,7 +1823,7 @@ function readStyle(node, objectStack) { const type = geometry.getType(); if (type === GeometryType.GEOMETRY_COLLECTION) { return new GeometryCollection( - geometry.getGeometriesArray().filter(function(geometry) { + geometry.getGeometriesArrayRecursive().filter(function(geometry) { const type = geometry.getType(); return type === GeometryType.POLYGON || type === GeometryType.MULTI_POLYGON; }) @@ -2703,20 +2699,35 @@ function writeMultiGeometry(node, geometry, objectStack) { const context = {node: node}; const type = geometry.getType(); /** @type {Array} */ - let geometries; + let geometries = []; /** @type {function(*, Array<*>, string=): (Node|undefined)} */ let factory; - if (type == GeometryType.GEOMETRY_COLLECTION) { - geometries = /** @type {GeometryCollection} */ (geometry).getGeometries(); + if (type === GeometryType.GEOMETRY_COLLECTION) { + /** @type {GeometryCollection} */ (geometry).getGeometriesArrayRecursive().forEach(function(geometry) { + const type = geometry.getType(); + if (type === GeometryType.MULTI_POINT) { + geometries = geometries.concat(/** @type {MultiPoint} */ (geometry).getPoints()); + } else if (type === GeometryType.MULTI_LINE_STRING) { + geometries = geometries.concat(/** @type {MultiLineString} */ (geometry).getLineStrings()); + } else if (type === GeometryType.MULTI_POLYGON) { + geometries = geometries.concat(/** @type {MultiPolygon} */ (geometry).getPolygons()); + } else if (type === GeometryType.POINT + || type === GeometryType.LINE_STRING + || type === GeometryType.POLYGON) { + geometries.push(geometry); + } else { + assert(false, 39); // Unknown geometry type + } + }); factory = GEOMETRY_NODE_FACTORY; - } else if (type == GeometryType.MULTI_POINT) { + } else if (type === GeometryType.MULTI_POINT) { geometries = /** @type {MultiPoint} */ (geometry).getPoints(); factory = POINT_NODE_FACTORY; - } else if (type == GeometryType.MULTI_LINE_STRING) { + } else if (type === GeometryType.MULTI_LINE_STRING) { geometries = (/** @type {MultiLineString} */ (geometry)).getLineStrings(); factory = LINE_STRING_NODE_FACTORY; - } else if (type == GeometryType.MULTI_POLYGON) { + } else if (type === GeometryType.MULTI_POLYGON) { geometries = (/** @type {MultiPolygon} */ (geometry)).getPolygons(); factory = POLYGON_NODE_FACTORY; @@ -2831,13 +2842,61 @@ function writePlacemark(node, feature, objectStack) { // resolution-independent here const styles = styleFunction(feature, 0); if (styles) { - const style = Array.isArray(styles) ? styles[0] : styles; - if (this.writeStyles_) { - properties['Style'] = style; + const styleArray = Array.isArray(styles) ? styles : [styles]; + let pointStyles = styleArray; + if (feature.getGeometry()) { + pointStyles = styleArray.filter(function(style) { + const geometry = style.getGeometryFunction()(feature); + if (geometry) { + const type = geometry.getType(); + if (type === GeometryType.GEOMETRY_COLLECTION) { + return /** @type {GeometryCollection} */ (geometry).getGeometriesArrayRecursive().filter(function(geometry) { + const type = geometry.getType(); + return type === GeometryType.POINT || type === GeometryType.MULTI_POINT; + }).length; + } + return type === GeometryType.POINT || type === GeometryType.MULTI_POINT; + } + }); } - const textStyle = style.getText(); - if (textStyle) { - properties['name'] = textStyle.getText(); + if (this.writeStyles_) { + let lineStyles = styleArray; + let polyStyles = styleArray; + if (feature.getGeometry()) { + lineStyles = styleArray.filter(function(style) { + const geometry = style.getGeometryFunction()(feature); + if (geometry) { + const type = geometry.getType(); + if (type === GeometryType.GEOMETRY_COLLECTION) { + return /** @type {GeometryCollection} */ (geometry).getGeometriesArrayRecursive().filter(function(geometry) { + const type = geometry.getType(); + return type === GeometryType.LINE_STRING || type === GeometryType.MULTI_LINE_STRING; + }).length; + } + return type === GeometryType.LINE_STRING || type === GeometryType.MULTI_LINE_STRING; + } + }); + polyStyles = styleArray.filter(function(style) { + const geometry = style.getGeometryFunction()(feature); + if (geometry) { + const type = geometry.getType(); + if (type === GeometryType.GEOMETRY_COLLECTION) { + return /** @type {GeometryCollection} */ (geometry).getGeometriesArrayRecursive().filter(function(geometry) { + const type = geometry.getType(); + return type === GeometryType.POLYGON || type === GeometryType.MULTI_POLYGON; + }).length; + } + return type === GeometryType.POLYGON || type === GeometryType.MULTI_POLYGON; + } + }); + } + properties['Style'] = {pointStyles: pointStyles, lineStyles: lineStyles, polyStyles: polyStyles}; + } + if (pointStyles.length && properties['name'] === undefined) { + const textStyle = pointStyles[0].getText(); + if (textStyle) { + properties['name'] = textStyle.getText(); + } } } } @@ -2913,6 +2972,17 @@ function writePrimitiveGeometry(node, geometry, objectStack) { } +/** + * @const + * @type {Object>} + */ +// @ts-ignore +const POLY_STYLE_SEQUENCE = makeStructureNS( + NAMESPACE_URIS, [ + 'color', 'fill', 'outline' + ]); + + /** * @const * @type {Object>} @@ -2972,27 +3042,31 @@ function writePolygon(node, polygon, objectStack) { // @ts-ignore const POLY_STYLE_SERIALIZERS = makeStructureNS( NAMESPACE_URIS, { - 'color': makeChildAppender(writeColorTextNode) + 'color': makeChildAppender(writeColorTextNode), + 'fill': makeChildAppender(writeBooleanTextNode), + 'outline': makeChildAppender(writeBooleanTextNode) }); -/** - * A factory for creating coordinates nodes. - * @const - * @type {function(*, Array<*>, string=): (Node|undefined)} - */ -const COLOR_NODE_FACTORY = makeSimpleNodeFactory('color'); - - /** * @param {Node} node Node. - * @param {Fill} style Style. + * @param {Style} style Style. * @param {Array<*>} objectStack Object stack. */ function writePolyStyle(node, style, objectStack) { const /** @type {import("../xml.js").NodeStackItem} */ context = {node: node}; + const fill = style.getFill(); + const stroke = style.getStroke(); + const properties = { + 'color': fill ? fill.getColor() : undefined, + 'fill': fill ? undefined : false, + 'outline': stroke ? undefined : false + }; + const parentNode = objectStack[objectStack.length - 1].node; + const orderedKeys = POLY_STYLE_SEQUENCE[parentNode.namespaceURI]; + const values = makeSequence(properties, orderedKeys); pushSerializeAndPop(context, POLY_STYLE_SERIALIZERS, - COLOR_NODE_FACTORY, [style.getColor()], objectStack); + OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); } @@ -3034,27 +3108,34 @@ const STYLE_SERIALIZERS = makeStructureNS( /** * @param {Node} node Node. - * @param {Style} style Style. + * @param {Object>} styles Styles. * @param {Array<*>} objectStack Object stack. */ -function writeStyle(node, style, objectStack) { +function writeStyle(node, styles, objectStack) { const /** @type {import("../xml.js").NodeStackItem} */ context = {node: node}; const properties = {}; - const fillStyle = style.getFill(); - const strokeStyle = style.getStroke(); - const imageStyle = style.getImage(); - const textStyle = style.getText(); - if (imageStyle && typeof /** @type {?} */ (imageStyle).getSrc === 'function') { - properties['IconStyle'] = imageStyle; + if (styles.pointStyles.length) { + const textStyle = styles.pointStyles[0].getText(); + if (textStyle) { + properties['LabelStyle'] = textStyle; + } + const imageStyle = styles.pointStyles[0].getImage(); + if (imageStyle && typeof /** @type {?} */ (imageStyle).getSrc === 'function') { + properties['IconStyle'] = imageStyle; + } } - if (textStyle) { - properties['LabelStyle'] = textStyle; + if (styles.lineStyles.length) { + const strokeStyle = styles.lineStyles[0].getStroke(); + if (strokeStyle) { + properties['LineStyle'] = strokeStyle; + } } - if (strokeStyle) { - properties['LineStyle'] = strokeStyle; - } - if (fillStyle) { - properties['PolyStyle'] = fillStyle; + if (styles.polyStyles.length) { + const strokeStyle = styles.polyStyles[0].getStroke(); + if (strokeStyle && !properties['LineStyle']) { + properties['LineStyle'] = strokeStyle; + } + properties['PolyStyle'] = styles.polyStyles[0]; } const parentNode = objectStack[objectStack.length - 1].node; const orderedKeys = STYLE_SEQUENCE[parentNode.namespaceURI]; diff --git a/src/ol/geom/GeometryCollection.js b/src/ol/geom/GeometryCollection.js index e1b63d76dd..1d407f2fdc 100644 --- a/src/ol/geom/GeometryCollection.js +++ b/src/ol/geom/GeometryCollection.js @@ -126,6 +126,23 @@ class GeometryCollection extends Geometry { return this.geometries_; } + /** + * @return {Array} Geometries. + */ + getGeometriesArrayRecursive() { + /** @type {Array} */ + let geometriesArray = []; + const geometries = this.geometries_; + for (let i = 0, ii = geometries.length; i < ii; ++i) { + if (geometries[i].getType() === this.getType()) { + geometriesArray = geometriesArray.concat(/** @type {GeometryCollection} */ (geometries[i]).getGeometriesArrayRecursive()); + } else { + geometriesArray.push(geometries[i]); + } + } + return geometriesArray; + } + /** * @inheritDoc */ diff --git a/test/spec/ol/format/kml.test.js b/test/spec/ol/format/kml.test.js index e1a248bb75..60d235387f 100644 --- a/test/spec/ol/format/kml.test.js +++ b/test/spec/ol/format/kml.test.js @@ -1207,9 +1207,16 @@ describe('ol.format.KML', function() { it('can write GeometryCollection geometries', function() { const collection = new GeometryCollection([ - new Point([1, 2]), - new LineString([[1, 2], [3, 4]]), - new Polygon([[[1, 2], [3, 4], [3, 2], [1, 2]]]) + new GeometryCollection([ + new Point([1, 2]), + new LineString([[1, 2], [3, 4]]), + new Polygon([[[1, 2], [3, 4], [3, 2], [1, 2]]]) + ]), + new GeometryCollection([ + new MultiPoint([[5, 6], [9, 10]]), + new MultiLineString([[[5, 6], [7, 8]], [[9, 10], [11, 12]]]), + new MultiPolygon([[[[5, 6], [7, 8], [7, 6], [5, 6]]], [[[9, 10], [11, 12], [11, 10], [9, 10]]]]) + ]) ]); const features = [new Feature(collection)]; const node = format.writeFeaturesNode(features); @@ -1234,6 +1241,32 @@ describe('ol.format.KML', function() { ' ' + ' ' + ' ' + + ' ' + + ' 5,6' + + ' ' + + ' ' + + ' 9,10' + + ' ' + + ' ' + + ' 5,6 7,8' + + ' ' + + ' ' + + ' 9,10 11,12' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 5,6 7,8 7,6 5,6' + + ' ' + + ' ' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 9,10 11,12 11,10 9,10' + + ' ' + + ' ' + + ' ' + ' ' + ' ' + ''; @@ -1621,6 +1654,9 @@ describe('ol.format.KML', function() { ' ff332211' + ' 2' + ' ' + + ' ' + + ' 0' + + ' ' + ' ' + ' ' + ' ' + @@ -2164,6 +2200,43 @@ describe('ol.format.KML', function() { expect(strokeStyle.getWidth()).to.be(9); expect(style.getText()).to.be(getDefaultTextStyle()); expect(style.getZIndex()).to.be(undefined); + + const lineString = new LineString([[1, 2], [3, 4]]); + const polygon = new Polygon([[[0, 0], [0, 2], [2, 2], [2, 0], [0, 0]]]); + const collection = new GeometryCollection([lineString, polygon]); + f.setGeometry(collection); + const node = format.writeFeaturesNode(fs); + const text1 = + '' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 1,2 3,4' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 0,0 0,2 2,2 2,0 0,0' + + ' ' + + ' ' + + ' ' + + ' ' + + ' ' + + ''; + expect(node).to.xmleql(parse(text1)); }); it('disables the stroke when outline is \'0\'', function() { @@ -2233,6 +2306,41 @@ describe('ol.format.KML', function() { expect(style1.getFill()).to.be(fillStyle); expect(style1.getStroke()).to.be(null); expect(style1.getZIndex()).to.be(undefined); + + f.setGeometry(collectionFeature.getGeometry()); + const node = format.writeFeaturesNode(fs); + const text1 = + '' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 1,2 3,4' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 0,0 0,2 2,2 2,0 0,0' + + ' ' + + ' ' + + ' ' + + ' ' + + ' ' + + ''; + expect(node).to.xmleql(parse(text1)); }); it('disables both fill and stroke when fill and outline are \'0\'', @@ -2302,6 +2410,41 @@ describe('ol.format.KML', function() { expect(style1.getFill()).to.be(null); expect(style1.getStroke()).to.be(null); expect(style1.getZIndex()).to.be(undefined); + + f.setGeometry(collectionFeature.getGeometry()); + const node = format.writeFeaturesNode(fs); + const text1 = + '' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 1,2 3,4' + + ' ' + + ' ' + + ' ' + + ' ' + + ' 0,0 0,2 2,2 2,0 0,0' + + ' ' + + ' ' + + ' ' + + ' ' + + ' ' + + ''; + expect(node).to.xmleql(parse(text1)); }); it('can create text style for named point placemarks (including html character codes)', function() { @@ -2392,6 +2535,10 @@ describe('ol.format.KML', function() { ' ' + ' ' + + ' ' + + ' 0' + + ' 0' + + ' ' + ' ' + ' ' + ''; @@ -2440,6 +2587,10 @@ describe('ol.format.KML', function() { ' https://developers.google.com/kml/schema/kml22gx.xsd">' + ' ' + ' ' + ' ' + ''; @@ -2472,13 +2623,17 @@ describe('ol.format.KML', function() { ' ffdf220c' + ' 0.5' + ' ' + + ' ' + + ' 0' + + ' 0' + + ' ' + ' ' + ' ' + ''; expect(node).to.xmleql(parse(text)); }); - it('can write an feature\'s stroke style', function() { + it('can write an feature\'s stroke style without fill', function() { const style = new Style({ stroke: new Stroke({ color: '#112233', @@ -2500,13 +2655,16 @@ describe('ol.format.KML', function() { ' ff332211' + ' 2' + ' ' + + ' ' + + ' 0' + + ' ' + ' ' + ' ' + ''; expect(node).to.xmleql(parse(text)); }); - it('can write an feature\'s fill style', function() { + it('can write an feature\'s fill style without outline', function() { const style = new Style({ fill: new Fill({ color: 'rgba(12, 34, 223, 0.7)' @@ -2525,6 +2683,41 @@ describe('ol.format.KML', function() { ' ' + + ' ' + + ''; + expect(node).to.xmleql(parse(text)); + }); + + it('can write an feature\'s fill style and outline', function() { + const style = new Style({ + fill: new Fill({ + color: 'rgba(12, 34, 223, 0.7)' + }), + stroke: new Stroke({ + color: '#112233', + width: 2 + }) + }); + const feature = new Feature(); + feature.setStyle([style]); + const node = format.writeFeaturesNode([feature]); + const text = + '' + + ' ' + + ' ' + ' ' + @@ -2554,6 +2747,7 @@ describe('ol.format.KML', function() { ' ' + ' ' + @@ -2561,6 +2755,7 @@ describe('ol.format.KML', function() { ' ' + ' ' + From 4ca966bd92a060e2bcc138ba1c1d2ad4f9b71e26 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Wed, 11 Mar 2020 14:09:33 +0000 Subject: [PATCH 007/119] show labels in wrapped worlds test labels in wrapped world --- src/ol/layer/Graticule.js | 91 ++++++++++++++++++++-------------- test/spec/ol/graticule.test.js | 48 ++++++++++++++++-- 2 files changed, 100 insertions(+), 39 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 0fbc0cea50..6bc7360dfa 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -17,6 +17,7 @@ import { import { applyTransform, containsCoordinate, + containsExtent, equals, getCenter, getHeight, @@ -622,9 +623,9 @@ class Graticule extends VectorLayer { drawLabels_(event) { const rotation = event.frameState.viewState.rotation; const extent = event.frameState.extent; - let rotationCenter, rotationExtent; + const rotationCenter = getCenter(extent); + let rotationExtent = extent; if (rotation) { - rotationCenter = getCenter(extent); const width = getWidth(extent); const height = getHeight(extent); const cr = Math.abs(Math.cos(rotation)); @@ -637,42 +638,60 @@ class Graticule extends VectorLayer { ]; } - const vectorContext = getVectorContext(event); - let poolIndex = this.meridians_.length + this.parallels_.length; - let feature, index, l, textPoint; - - if (this.meridiansLabels_) { - for (index = 0, l = this.meridiansLabels_.length; index < l; ++index) { - const lineString = this.meridians_[index]; - if (!rotation) { - textPoint = this.getMeridianPoint_(lineString, extent, index); - } else { - const clone = lineString.clone(); - clone.rotate(-rotation, rotationCenter); - textPoint = this.getMeridianPoint_(clone, rotationExtent, index); - textPoint.rotate(rotation, rotationCenter); - } - feature = this.featurePool_[poolIndex++]; - feature.setGeometry(textPoint); - feature.set('graticule_label', this.meridiansLabels_[index].text); - vectorContext.drawFeature(feature, this.lonLabelStyle_(feature)); - } + let startWorld = 0; + let endWorld = 0; + let labelsAtStart = this.latLabelPosition_ < 0.5; + const projectionExtent = this.projection_.getExtent(); + const worldWidth = getWidth(projectionExtent); + if (this.getSource().getWrapX() && this.projection_.canWrapX() && !containsExtent(projectionExtent, extent)) { + startWorld = Math.floor((extent[0] - projectionExtent[0]) / worldWidth); + endWorld = Math.ceil((extent[2] - projectionExtent[2]) / worldWidth); + const inverted = Math.abs(rotation) > Math.PI / 2; + labelsAtStart = labelsAtStart !== inverted; } - if (this.parallelsLabels_) { - for (index = 0, l = this.parallels_.length; index < l; ++index) { - const lineString = this.parallels_[index]; - if (!rotation) { - textPoint = this.getParallelPoint_(lineString, extent, index); - } else { - const clone = lineString.clone(); - clone.rotate(-rotation, rotationCenter); - textPoint = this.getParallelPoint_(clone, rotationExtent, index); - textPoint.rotate(rotation, rotationCenter); + const vectorContext = getVectorContext(event); + + for (let world = startWorld; world <= endWorld; ++world) { + let poolIndex = this.meridians_.length + this.parallels_.length; + let feature, index, l, textPoint; + + if (this.meridiansLabels_) { + for (index = 0, l = this.meridiansLabels_.length; index < l; ++index) { + const lineString = this.meridians_[index]; + if (!rotation && world === 0) { + textPoint = this.getMeridianPoint_(lineString, extent, index); + } else { + const clone = lineString.clone(); + clone.translate(world * worldWidth, 0); + clone.rotate(-rotation, rotationCenter); + textPoint = this.getMeridianPoint_(clone, rotationExtent, index); + textPoint.rotate(rotation, rotationCenter); + } + feature = this.featurePool_[poolIndex++]; + feature.setGeometry(textPoint); + feature.set('graticule_label', this.meridiansLabels_[index].text); + vectorContext.drawFeature(feature, this.lonLabelStyle_(feature)); + } + } + if (this.parallelsLabels_) { + if (world === startWorld && labelsAtStart || world === endWorld && !labelsAtStart) { + for (index = 0, l = this.parallels_.length; index < l; ++index) { + const lineString = this.parallels_[index]; + if (!rotation && world === 0) { + textPoint = this.getParallelPoint_(lineString, extent, index); + } else { + const clone = lineString.clone(); + clone.translate(world * worldWidth, 0); + clone.rotate(-rotation, rotationCenter); + textPoint = this.getParallelPoint_(clone, rotationExtent, index); + textPoint.rotate(rotation, rotationCenter); + } + feature = this.featurePool_[poolIndex++]; + feature.setGeometry(textPoint); + feature.set('graticule_label', this.parallelsLabels_[index].text); + vectorContext.drawFeature(feature, this.latLabelStyle_(feature)); + } } - feature = this.featurePool_[poolIndex++]; - feature.setGeometry(textPoint); - feature.set('graticule_label', this.parallelsLabels_[index].text); - vectorContext.drawFeature(feature, this.latLabelStyle_(feature)); } } } diff --git a/test/spec/ol/graticule.test.js b/test/spec/ol/graticule.test.js index 269c496578..366358cd82 100644 --- a/test/spec/ol/graticule.test.js +++ b/test/spec/ol/graticule.test.js @@ -1,6 +1,6 @@ import Graticule from '../../../src/ol/layer/Graticule.js'; import Map from '../../../src/ol/Map.js'; -import {get as getProjection} from '../../../src/ol/proj.js'; +import {fromLonLat, get as getProjection} from '../../../src/ol/proj.js'; import Stroke from '../../../src/ol/style/Stroke.js'; import Text from '../../../src/ol/style/Text.js'; import Feature from '../../../src/ol/Feature.js'; @@ -31,7 +31,48 @@ describe('ol.layer.Graticule', function() { expect(graticule.parallelsLabels_).to.be(null); }); - it('creates a graticule with labels', function() { + it('creates a graticule with normal world labels', function() { + const feature = new Feature(); + graticule = new Graticule({ + showLabels: true, + wrapX: false + }); + new Map({ + layers: [graticule] + }); + const extent = [-25614353.926475704, -7827151.696402049, + 25614353.926475704, 7827151.696402049]; + const projection = getProjection('EPSG:3857'); + const resolution = 39135.75848201024; + graticule.loaderFunction(extent, resolution, projection); + const event = { + context: document.createElement('canvas').getContext('2d'), + inversePixelTransform: [1, 0, 0, 1, 0, 0], + frameState: { + coordinateToPixelTransform: [1, 0, 0, 1, 0, 0], + extent: extent, + pixelRatio: 1, + viewState: { + projection: projection, + resolution: resolution, + rotation: 0 + } + } + }; + graticule.drawLabels_(event); + expect(graticule.meridiansLabels_.length).to.be(13); + expect(graticule.meridiansLabels_[0].text).to.be('0° 00′ 00″'); + expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(0, 1e-9); + expect(graticule.parallelsLabels_.length).to.be(3); + expect(graticule.parallelsLabels_[0].text).to.be('0° 00′ 00″'); + expect(graticule.parallelsLabels_[0].geom.getCoordinates()[1]).to.roughlyEqual(0, 1e-9); + feature.set('graticule_label', graticule.meridiansLabels_[0].text); + expect(graticule.lonLabelStyle_(feature).getText().getText()).to.be('0° 00′ 00″'); + feature.set('graticule_label', graticule.parallelsLabels_[0].text); + expect(graticule.latLabelStyle_(feature).getText().getText()).to.be('0° 00′ 00″'); + }); + + it('creates a graticule with wrapped world labels', function() { const feature = new Feature(); graticule = new Graticule({ showLabels: true @@ -61,7 +102,8 @@ describe('ol.layer.Graticule', function() { graticule.drawLabels_(event); expect(graticule.meridiansLabels_.length).to.be(13); expect(graticule.meridiansLabels_[0].text).to.be('0° 00′ 00″'); - expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(0, 1e-9); + const coordinates = fromLonLat([360, 0]); + expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(coordinates[0], 1e-9); expect(graticule.parallelsLabels_.length).to.be(3); expect(graticule.parallelsLabels_[0].text).to.be('0° 00′ 00″'); expect(graticule.parallelsLabels_[0].geom.getCoordinates()[1]).to.roughlyEqual(0, 1e-9); From 092a199757d7e168c90ed94c6549b8c1b0ce2a9e Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Thu, 12 Mar 2020 08:57:32 +0100 Subject: [PATCH 008/119] Make Overlay.panIntoView an API method * Add parameters for custom animation parameters and margin * Add protected wrapper method for previous autoPan functionality See #10741 --- src/ol/Overlay.js | 35 ++++++++++++++++++++++++----------- 1 file changed, 24 insertions(+), 11 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index fa71db0591..89bca14238 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -323,7 +323,7 @@ class Overlay extends BaseObject { handlePositionChanged() { this.updatePixelPosition(); if (this.get(Property.POSITION) && this.autoPan) { - this.panIntoView(); + this.performAutoPan(); } } @@ -378,11 +378,23 @@ class Overlay extends BaseObject { } /** - * Pan the map so that the overlay is entirely visible in the current viewport - * (if necessary). + * Pan the map so that the overlay is entirely visisbly in the current viewport + * (if necessary) using the configured autoPan parameters * @protected */ - panIntoView() { + performAutoPan() { + this.panIntoView(this.autoPanAnimation, this.autoPanMargin); + } + + /** + * Pan the map so that the overlay is entirely visible in the current viewport + * (if necessary). + * @param {PanOptions|undefined} panOptions Animation options for the pan action + * @param {number|undefined} margin The margin (in pixels) between the overlay and the + * borders of the map when autopanning + * @api + */ + panIntoView(panOptions, margin) { const map = this.getMap(); if (!map || !map.getTargetElement()) { @@ -393,7 +405,7 @@ class Overlay extends BaseObject { const element = this.getElement(); const overlayRect = this.getRect(element, [outerWidth(element), outerHeight(element)]); - const margin = this.autoPanMargin; + const myMargin = (margin === undefined) ? 20 : margin; if (!containsExtent(mapRect, overlayRect)) { // the overlay is not completely inside the viewport, so pan the map const offsetLeft = overlayRect[0] - mapRect[0]; @@ -404,17 +416,17 @@ class Overlay extends BaseObject { const delta = [0, 0]; if (offsetLeft < 0) { // move map to the left - delta[0] = offsetLeft - margin; + delta[0] = offsetLeft - myMargin; } else if (offsetRight < 0) { // move map to the right - delta[0] = Math.abs(offsetRight) + margin; + delta[0] = Math.abs(offsetRight) + myMargin; } if (offsetTop < 0) { // move map up - delta[1] = offsetTop - margin; + delta[1] = offsetTop - myMargin; } else if (offsetBottom < 0) { // move map down - delta[1] = Math.abs(offsetBottom) + margin; + delta[1] = Math.abs(offsetBottom) + myMargin; } if (delta[0] !== 0 || delta[1] !== 0) { @@ -425,10 +437,11 @@ class Overlay extends BaseObject { centerPx[1] + delta[1] ]; + const myPanOptions = panOptions || {}; map.getView().animateInternal({ center: map.getCoordinateFromPixelInternal(newCenterPx), - duration: this.autoPanAnimation.duration, - easing: this.autoPanAnimation.easing + duration: myPanOptions.duration, + easing: myPanOptions.easing }); } } From 022caae848b315ab8d8f717c8896a3b9c486538a Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Thu, 12 Mar 2020 09:37:40 +0100 Subject: [PATCH 009/119] Document default margin in Overlay.panIntoView --- src/ol/Overlay.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index 89bca14238..b682f0ff4f 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -378,7 +378,7 @@ class Overlay extends BaseObject { } /** - * Pan the map so that the overlay is entirely visisbly in the current viewport + * Pan the map so that the overlay is entirely visisble in the current viewport * (if necessary) using the configured autoPan parameters * @protected */ @@ -390,7 +390,7 @@ class Overlay extends BaseObject { * Pan the map so that the overlay is entirely visible in the current viewport * (if necessary). * @param {PanOptions|undefined} panOptions Animation options for the pan action - * @param {number|undefined} margin The margin (in pixels) between the overlay and the + * @param {number|undefined} [margin=20] The margin (in pixels) between the overlay and the * borders of the map when autopanning * @api */ From 058ca592332d6642745f3b35633f94e43ac8f5cf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Thu, 12 Mar 2020 21:36:19 +0100 Subject: [PATCH 010/119] Also correctly detect default exports without an identifier --- config/jsdoc/api/plugins/api.js | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/config/jsdoc/api/plugins/api.js b/config/jsdoc/api/plugins/api.js index 0c4d80e85e..2d4cc92432 100644 --- a/config/jsdoc/api/plugins/api.js +++ b/config/jsdoc/api/plugins/api.js @@ -113,9 +113,10 @@ const moduleRoot = path.join(process.cwd(), 'src'); // Tag default exported Identifiers because their name should be the same as the module name. exports.astNodeVisitor = { visitNode: function(node, e, parser, currentSourceName) { - if (node.type === 'Identifier' && node.parent.type === 'ExportDefaultDeclaration') { + if (node.parent && node.parent.type === 'ExportDefaultDeclaration') { const modulePath = path.relative(moduleRoot, currentSourceName).replace(/\.js$/, ''); - defaultExports['module:' + modulePath.replace(/\\/g, '/') + '~' + node.name] = true; + const exportName = 'module:' + modulePath.replace(/\\/g, '/') + (node.name ? '~' + node.name : ''); + defaultExports[exportName] = true; } } }; From f2477622c38067ac9887ebead68361e8d9c2a01f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Thu, 12 Mar 2020 22:23:28 +0100 Subject: [PATCH 011/119] Remove redundant check if doclet kind is typedef --- config/jsdoc/api/plugins/api.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/config/jsdoc/api/plugins/api.js b/config/jsdoc/api/plugins/api.js index 2d4cc92432..93ff1de5cb 100644 --- a/config/jsdoc/api/plugins/api.js +++ b/config/jsdoc/api/plugins/api.js @@ -181,7 +181,7 @@ exports.handlers = { doclet._hideConstructor = true; includeAugments(doclet); sortOtherMembers(doclet); - } else if (!doclet._hideConstructor && !(doclet.kind == 'typedef' && doclet.longname in types)) { + } else if (!doclet._hideConstructor) { // Remove all other undocumented symbols doclet.undocumented = true; } From 873cccc4f3c6b08cfd35b24e62d30a926700412c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Thu, 12 Mar 2020 22:29:00 +0100 Subject: [PATCH 012/119] Add default exported enums to apidoc --- config/jsdoc/api/plugins/api.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/config/jsdoc/api/plugins/api.js b/config/jsdoc/api/plugins/api.js index 93ff1de5cb..c384d86dad 100644 --- a/config/jsdoc/api/plugins/api.js +++ b/config/jsdoc/api/plugins/api.js @@ -157,6 +157,7 @@ exports.handlers = { parseComplete: function(e) { const doclets = e.doclets; + const byLongname = doclets.index.longname; for (let i = doclets.length - 1; i >= 0; --i) { const doclet = doclets[i]; if (doclet.stability) { @@ -181,7 +182,8 @@ exports.handlers = { doclet._hideConstructor = true; includeAugments(doclet); sortOtherMembers(doclet); - } else if (!doclet._hideConstructor) { + } else if (!doclet._hideConstructor + && !(doclet.longname in defaultExports && byLongname[doclet.longname].some(d => d.isEnum))) { // Remove all other undocumented symbols doclet.undocumented = true; } From 859bf338a250ef52d05173ca0696e253babaff20 Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Fri, 13 Mar 2020 10:05:18 +0100 Subject: [PATCH 013/119] Use Object for options to Overlay panIntoView * animation and margin encapsulated in a single object to allow easier extension in future * Constructor options extended to allow single object for autoPan; separate options still allowed but deprecated * Protected fields for animation and margin replaced with single field --- src/ol/Overlay.js | 50 +++++++++++++++++++++++++---------------------- 1 file changed, 27 insertions(+), 23 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index b682f0ff4f..941aadda3d 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -40,12 +40,16 @@ import {containsExtent} from './extent.js'; * @property {boolean} [autoPan=false] If set to `true` the map is panned when * calling `setPosition`, so that the overlay is entirely visible in the current * viewport. - * @property {PanOptions} [autoPanAnimation] The - * animation options used to pan the overlay into view. This animation is only - * used when `autoPan` is enabled. A `duration` and `easing` may be provided to - * customize the animation. + * @property {PanOptions} [autoPanAnimation] The animation options used to pan + * the overlay into view. This animation is only used when `autoPan` is enabled. + * A `duration` and `easing` may be provided to customize the animation. + * Deprecated and ignored if `autoPanOptions` is supplied. * @property {number} [autoPanMargin=20] The margin (in pixels) between the - * overlay and the borders of the map when autopanning. + * overlay and the borders of the map when autopanning. Deprecated and ignored + * if `autoPanOptions` is supplied. + * @property {PanIntoViewOptions} [autoPanOptions] The options to use for the + * autoPan. This is only used when `autoPan` is enabled and has preference over + * the individual `autoPanMargin` and `autoPanOptions`. * @property {string} [className='ol-overlay-container ol-selectable'] CSS class * name. */ @@ -60,6 +64,12 @@ import {containsExtent} from './extent.js'; * Default is {@link module:ol/easing~inAndOut}. */ +/** + * @typedef {Object} PanIntoViewOptions + * @property {PanOptions} [animation={}] The animation parameters for the pan + * @property {number} [margin=20] The margin (in pixels) between the + * overlay and the borders of the map when panning into view. + */ /** * @enum {string} @@ -145,16 +155,12 @@ class Overlay extends BaseObject { /** * @protected - * @type {PanOptions} + * @type {PanIntoViewOptions} */ - this.autoPanAnimation = options.autoPanAnimation || /** @type {PanOptions} */ ({}); - - /** - * @protected - * @type {number} - */ - this.autoPanMargin = options.autoPanMargin !== undefined ? - options.autoPanMargin : 20; + this.autoPanOptions = options.autoPanOptions || { + animation: options.autoPanAnimation, + margin: options.autoPanMargin + }; /** * @protected @@ -383,18 +389,16 @@ class Overlay extends BaseObject { * @protected */ performAutoPan() { - this.panIntoView(this.autoPanAnimation, this.autoPanMargin); + this.panIntoView(this.autoPanOptions); } /** * Pan the map so that the overlay is entirely visible in the current viewport * (if necessary). - * @param {PanOptions|undefined} panOptions Animation options for the pan action - * @param {number|undefined} [margin=20] The margin (in pixels) between the overlay and the - * borders of the map when autopanning + * @param {PanIntoViewOptions|undefined} panIntoViewOptions Options for the pan action * @api */ - panIntoView(panOptions, margin) { + panIntoView(panIntoViewOptions) { const map = this.getMap(); if (!map || !map.getTargetElement()) { @@ -405,7 +409,7 @@ class Overlay extends BaseObject { const element = this.getElement(); const overlayRect = this.getRect(element, [outerWidth(element), outerHeight(element)]); - const myMargin = (margin === undefined) ? 20 : margin; + const myMargin = (panIntoViewOptions.margin === undefined) ? 20 : panIntoViewOptions.margin; if (!containsExtent(mapRect, overlayRect)) { // the overlay is not completely inside the viewport, so pan the map const offsetLeft = overlayRect[0] - mapRect[0]; @@ -437,11 +441,11 @@ class Overlay extends BaseObject { centerPx[1] + delta[1] ]; - const myPanOptions = panOptions || {}; + const panOptions = panIntoViewOptions.animation || {}; map.getView().animateInternal({ center: map.getCoordinateFromPixelInternal(newCenterPx), - duration: myPanOptions.duration, - easing: myPanOptions.easing + duration: panOptions.duration, + easing: panOptions.easing }); } } From 406c38403b5507c6459c3fe4d5a2def2cd5de8be Mon Sep 17 00:00:00 2001 From: regileeso Date: Fri, 13 Mar 2020 11:36:20 +0000 Subject: [PATCH 014/119] make ImageSourceEventType available for consumers --- src/ol/source/Image.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/source/Image.js b/src/ol/source/Image.js index 7d5cf0e4ce..cf93b63ebe 100644 --- a/src/ol/source/Image.js +++ b/src/ol/source/Image.js @@ -15,7 +15,7 @@ import Source from './Source.js'; /** * @enum {string} */ -const ImageSourceEventType = { +export const ImageSourceEventType = { /** * Triggered when an image starts loading. From 3c1ad1fc1d64495766312f05991feb6dfde340da Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Fri, 13 Mar 2020 21:23:16 +0000 Subject: [PATCH 015/119] [Security] Bump acorn from 6.1.1 to 6.4.1 Bumps [acorn](https://github.com/acornjs/acorn) from 6.1.1 to 6.4.1. **This update includes a security fix.** - [Release notes](https://github.com/acornjs/acorn/releases) - [Commits](https://github.com/acornjs/acorn/compare/6.1.1...6.4.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/package-lock.json b/package-lock.json index 96ff963fd1..c1e416b0a1 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1927,9 +1927,9 @@ } }, "acorn": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.1.1.tgz", - "integrity": "sha512-jPTiwtOxaHNaAPg/dmrJ/beuzLRnXtB0kQPQ8JpotKJgTB6rX6c8mlf315941pyjBSaPg8NHXS9fhP4u17DpGA==", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.4.1.tgz", + "integrity": "sha512-ZVA9k326Nwrj3Cj9jlh3wGFutC2ZornPNARZwsNYqQYgN0EsV2d53w5RN/co65Ohn4sUAUtb1rSUAOD6XN9idA==", "dev": true }, "acorn-dynamic-import": { @@ -4516,9 +4516,9 @@ }, "dependencies": { "acorn": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.1.0.tgz", - "integrity": "sha512-kL5CuoXA/dgxlBbVrflsflzQ3PAas7RYZB52NOm/6839iVYJgKMJ3cQJD+t2i5+qFa8h3MDpEOJiS64E8JLnSQ==", + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.1.1.tgz", + "integrity": "sha512-add7dgA5ppRPxCFJoAGfMDi7PIBXq1RtGo7BhbLaxwrXPOmw8gq48Y9ozT01hUKy9byMjlR20EJhu5zlkErEkg==", "dev": true }, "acorn-jsx": { @@ -12103,12 +12103,6 @@ "webpack-sources": "^1.4.1" }, "dependencies": { - "acorn": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.4.0.tgz", - "integrity": "sha512-gac8OEcQ2Li1dxIEWGZzsp2BitJxwkwcOm0zHAJLcPJaVvm58FRnk6RkuLRpU1EujipU2ZFODv2P9DLMfnV8mw==", - "dev": true - }, "ajv": { "version": "6.12.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.0.tgz", From 47ce1490f8440cc653ef2c14a243e8038208613a Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 16 Mar 2020 08:19:01 +0000 Subject: [PATCH 016/119] Bump yargs from 15.3.0 to 15.3.1 Bumps [yargs](https://github.com/yargs/yargs) from 15.3.0 to 15.3.1. - [Release notes](https://github.com/yargs/yargs/releases) - [Changelog](https://github.com/yargs/yargs/blob/master/CHANGELOG.md) - [Commits](https://github.com/yargs/yargs/compare/v15.3.0...v15.3.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/package-lock.json b/package-lock.json index c1e416b0a1..805859fd42 100644 --- a/package-lock.json +++ b/package-lock.json @@ -12598,9 +12598,9 @@ "dev": true }, "yargs": { - "version": "15.3.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.3.0.tgz", - "integrity": "sha512-g/QCnmjgOl1YJjGsnUg2SatC7NUYEiLXJqxNOQU9qSpjzGtGXda9b+OKccr1kLTy8BN9yqEyqfq5lxlwdc13TA==", + "version": "15.3.1", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.3.1.tgz", + "integrity": "sha512-92O1HWEjw27sBfgmXiixJWT5hRBp2eobqXicLtPBIDBhYB+1HpwZlXmbW2luivBJHBzki+7VyCLRtAkScbTBQA==", "dev": true, "requires": { "cliui": "^6.0.0", @@ -12613,7 +12613,7 @@ "string-width": "^4.2.0", "which-module": "^2.0.0", "y18n": "^4.0.0", - "yargs-parser": "^18.1.0" + "yargs-parser": "^18.1.1" }, "dependencies": { "ansi-regex": { @@ -12736,9 +12736,9 @@ } }, "yargs-parser": { - "version": "18.1.0", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.0.tgz", - "integrity": "sha512-o/Jr6JBOv6Yx3pL+5naWSoIA2jJ+ZkMYQG/ie9qFbukBe4uzmBatlXFOiu/tNKRWEtyf+n5w7jc/O16ufqOTdQ==", + "version": "18.1.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.1.tgz", + "integrity": "sha512-KRHEsOM16IX7XuLnMOqImcPNbLVXMNHYAoFc3BKR8Ortl5gzDbtXvvEoGx9imk5E+X1VeNKNlcHr8B8vi+7ipA==", "dev": true, "requires": { "camelcase": "^5.0.0", From 7bc7affccc4e8b2b76a74d67c9376c99955fc7fa Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 16 Mar 2020 08:20:12 +0000 Subject: [PATCH 017/119] Bump rollup-plugin-terser from 5.2.0 to 5.3.0 Bumps [rollup-plugin-terser](https://github.com/TrySound/rollup-plugin-terser) from 5.2.0 to 5.3.0. - [Release notes](https://github.com/TrySound/rollup-plugin-terser/releases) - [Commits](https://github.com/TrySound/rollup-plugin-terser/compare/v5.2.0...v5.3.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 31 ++++++++++--------------------- 1 file changed, 10 insertions(+), 21 deletions(-) diff --git a/package-lock.json b/package-lock.json index c1e416b0a1..7cf7f326be 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10021,9 +10021,9 @@ } }, "rollup-plugin-terser": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/rollup-plugin-terser/-/rollup-plugin-terser-5.2.0.tgz", - "integrity": "sha512-jQI+nYhtDBc9HFRBz8iGttQg7li9klmzR62RG2W2nN6hJ/FI2K2ItYQ7kJ7/zn+vs+BP1AEccmVRjRN989I+Nw==", + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/rollup-plugin-terser/-/rollup-plugin-terser-5.3.0.tgz", + "integrity": "sha512-XGMJihTIO3eIBsVGq7jiNYOdDMb3pVxuzY0uhOE/FM4x/u9nQgr3+McsjzqBn3QfHIpNSZmFnpoKAwHBEcsT7g==", "dev": true, "requires": { "@babel/code-frame": "^7.5.5", @@ -10034,18 +10034,18 @@ }, "dependencies": { "@babel/code-frame": { - "version": "7.8.0", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.8.0.tgz", - "integrity": "sha512-AN2IR/wCUYsM+PdErq6Bp3RFTXl8W0p9Nmymm7zkpsCmh+r/YYcckaCGpU8Q/mEKmST19kkGRaG42A/jxOWwBA==", + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.8.3.tgz", + "integrity": "sha512-a9gxpmdXtZEInkCSHUJDLHZVBgb1QS0jhss4cPP93EW7s+uC5bikET2twEF3KV+7rDblJcmNvTR7VJejqd2C2g==", "dev": true, "requires": { - "@babel/highlight": "^7.8.0" + "@babel/highlight": "^7.8.3" } }, "@babel/highlight": { - "version": "7.8.0", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.8.0.tgz", - "integrity": "sha512-OsdTJbHlPtIk2mmtwXItYrdmalJ8T0zpVzNAbKSkHshuywj7zb29Y09McV/jQsQunc/nEyHiPV2oy9llYMLqxw==", + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.8.3.tgz", + "integrity": "sha512-PX4y5xQUvy0fnEVHrYOarRPXVWafSjTW9T0Hab8gVIawpl2Sj0ORyrygANq+KjcNlSSTw0YCLSNA8OyZ1I4yEg==", "dev": true, "requires": { "chalk": "^2.0.0", @@ -10061,17 +10061,6 @@ "requires": { "estree-walker": "^0.6.1" } - }, - "terser": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/terser/-/terser-4.6.2.tgz", - "integrity": "sha512-6FUjJdY2i3WZAtYBtnV06OOcOfzl+4hSKYE9wgac8rkLRBToPDDrBB2AcHwQD/OKDxbnvhVy2YgOPWO2SsKWqg==", - "dev": true, - "requires": { - "commander": "^2.20.0", - "source-map": "~0.6.1", - "source-map-support": "~0.5.12" - } } } }, From 21b2d8aa482de522225eccb932a2f1308fc7d114 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 16 Mar 2020 08:21:07 +0000 Subject: [PATCH 018/119] Bump sinon from 9.0.0 to 9.0.1 Bumps [sinon](https://github.com/sinonjs/sinon) from 9.0.0 to 9.0.1. - [Release notes](https://github.com/sinonjs/sinon/releases) - [Changelog](https://github.com/sinonjs/sinon/blob/master/CHANGELOG.md) - [Commits](https://github.com/sinonjs/sinon/compare/v9.0.0...v9.0.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 30 ++++++++++++++---------------- 1 file changed, 14 insertions(+), 16 deletions(-) diff --git a/package-lock.json b/package-lock.json index c1e416b0a1..45b866c264 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1622,13 +1622,12 @@ } }, "@sinonjs/samsam": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/@sinonjs/samsam/-/samsam-5.0.2.tgz", - "integrity": "sha512-p3yrEVB5F/1wI+835n+X8llOGRgV8+jw5BHQ/cJoLBUXXZ5U8Tr5ApwPc4L4av/vjla48kVPoN0t6dykQm+Rvg==", + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/@sinonjs/samsam/-/samsam-5.0.3.tgz", + "integrity": "sha512-QucHkc2uMJ0pFGjJUDP3F9dq5dx8QIaqISl9QgwLOh6P9yv877uONPGXh/OH/0zmM3tW1JjuJltAZV2l7zU+uQ==", "dev": true, "requires": { "@sinonjs/commons": "^1.6.0", - "@sinonjs/formatio": "^5.0.0", "lodash.get": "^4.4.2", "type-detect": "^4.0.8" } @@ -7350,9 +7349,9 @@ } }, "just-extend": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/just-extend/-/just-extend-4.0.2.tgz", - "integrity": "sha512-FrLwOgm+iXrPV+5zDU6Jqu4gCRXbWEQg2O3SKONsWE4w7AXFRkryS53bpWdaL9cNol+AmR3AEYz6kn+o0fCPnw==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/just-extend/-/just-extend-4.1.0.tgz", + "integrity": "sha512-ApcjaOdVTJ7y4r08xI5wIqpvwS48Q0PBG4DJROcEkH1f8MdAiNFyFxz3xoL0LWAVwjrwPYZdVHHxhRHcx/uGLA==", "dev": true }, "karma": { @@ -8461,14 +8460,13 @@ "dev": true }, "nise": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/nise/-/nise-4.0.2.tgz", - "integrity": "sha512-ALDnm0pTTyeGdbg5FCpWGd58Nmp3qO8d8x+dU2Fw8lApeJTEBSjkBZZM4S8t6GpKh+czxkfM/TKxpRMroZzwOg==", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/nise/-/nise-4.0.3.tgz", + "integrity": "sha512-EGlhjm7/4KvmmE6B/UFsKh7eHykRl9VH+au8dduHLCyWUO/hr7+N+WtTvDUwc9zHuM1IaIJs/0lQ6Ag1jDkQSg==", "dev": true, "requires": { "@sinonjs/commons": "^1.7.0", "@sinonjs/fake-timers": "^6.0.0", - "@sinonjs/formatio": "^5.0.1", "@sinonjs/text-encoding": "^0.7.1", "just-extend": "^4.0.2", "path-to-regexp": "^1.7.0" @@ -10460,15 +10458,15 @@ "dev": true }, "sinon": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/sinon/-/sinon-9.0.0.tgz", - "integrity": "sha512-c4bREcvuK5VuEGyMW/Oim9I3Rq49Vzb0aMdxouFaA44QCFpilc5LJOugrX+mkrvikbqCimxuK+4cnHVNnLR41g==", + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/sinon/-/sinon-9.0.1.tgz", + "integrity": "sha512-iTTyiQo5T94jrOx7X7QLBZyucUJ2WvL9J13+96HMfm2CGoJYbIPqRfl6wgNcqmzk0DI28jeGx5bUTXizkrqBmg==", "dev": true, "requires": { "@sinonjs/commons": "^1.7.0", "@sinonjs/fake-timers": "^6.0.0", - "@sinonjs/formatio": "^5.0.0", - "@sinonjs/samsam": "^5.0.1", + "@sinonjs/formatio": "^5.0.1", + "@sinonjs/samsam": "^5.0.3", "diff": "^4.0.2", "nise": "^4.0.1", "supports-color": "^7.1.0" From dca694ccc9747f5089bea1f02f9739a770f628a5 Mon Sep 17 00:00:00 2001 From: Tim Schaub Date: Mon, 16 Mar 2020 17:10:49 -0600 Subject: [PATCH 019/119] Add sponsors section to the readme --- README.md | 12 ++++++++++++ sponsor-logos/pozi.png | Bin 0 -> 2881 bytes 2 files changed, 12 insertions(+) create mode 100644 sponsor-logos/pozi.png diff --git a/README.md b/README.md index 89d6c0fbd3..7c789b6835 100644 --- a/README.md +++ b/README.md @@ -41,6 +41,18 @@ See the following examples for more detail on bundling OpenLayers with your appl * Using [Parcel](https://github.com/openlayers/ol-parcel) * Using [Browserify](https://github.com/openlayers/ol-browserify) +## Sponsors + +OpenLayers appreciates contributions of all kinds. We especially want to thank our fiscal sponsors who contribute to ongoing project maintenance. + +![Pozi logo](./sponsor-logos/pozi.png) + +> Pozi helps connect communities through spatial thinking. +> We love Openlayers and it forms a core part of our platform. +> https://pozi.com/ https://app.pozi.com/ + +See our [Open Collective](https://opencollective.com/openlayers/contribute/sponsors-214/checkout) page if you too are interested in becoming a regular sponsor. + ## Supported Browsers OpenLayers runs on all modern browsers that support [HTML5](https://html.spec.whatwg.org/multipage/) and [ECMAScript 5](http://www.ecma-international.org/ecma-262/5.1/). This includes Chrome, Firefox, Safari and Edge. For older browsers and platforms like Internet Explorer (down to version 9) and Android 4.x, [polyfills](http://polyfill.io) for `requestAnimationFrame` and `Element.prototype.classList` are required, and using the KML format requires a polyfill for `URL`. diff --git a/sponsor-logos/pozi.png b/sponsor-logos/pozi.png new file mode 100644 index 0000000000000000000000000000000000000000..843ee3e1181a2348211cd703902862f89c62053b GIT binary patch literal 2881 zcmV-H3%>M;P)4^Nq63e@<2Qo1)5p zw1~h*z*;1ZM=uEyn4O({j3j^EFn;CYhZxRMwe9Jq3AbRXpL=Mm@-Y5{DtLh;FNpI$ zn+lGWoS!7dGlua330@(AYewKY34B3_o~xF?>jZcgOCp2e6Fb=VSNtu+4ej2z*@Dkj>6+ z`r5iekcU|_nAvCq=ep#p6LV}}l?<Z z-Z@UgiFtEuVC}89J=s@=YV0Kti9wRDPK1IM%8r62|%l}&V-qg4$I7ZftV7%}MSXLP0q&03{3t;KPgYF0o zh-b_vW=c4Nm|JHFXxVAjI7&8}PEibo!EBzUml z(NpNRaauEaH7|uEcsm4$-2zV;hBuACofO%S;I6d*mcBg9HuiEpV9)P9dGJ+p>$wABd`nL33t?}t`w!<*)F?IfGS;0;-z|HE$ zQ3KgCRI4j1CbUrbdI1&*90p5v!mv|8l1Nbs1c^WVnW z)pFIWB&f$x%ksag-ueSe$DY4!e zbGq1BVIN?Xg8O4M>oG@rz?EJS7^K)}vG$F?97%RCv_wuNuv~%YNxqS6Mh}dQU^>X= zL89AE+n)L};sWz&OE_OJ?o;h%+v=N65?I3nb|0NiUQ2uHR-6P?hU2XUfqGQqd%g)a z^}uomaPMEYeYdFdSBUZ76kyaRxKg%1+xUV6@A=BTc{N<6DnBre-R9D4pC<(@wJlO2 zGTdFEY84VZ;pMZ397FYq;jrb?rc(*5-2%^rRIDXj2V9+oRN;R^3@_xvH4-?#@a~_r z#CTUVoSr?!`q$-px4;iAJ+X8Wz-pGV8c)Uf$Uk%GF`Vs-)p5#oRk%V7SNkoQ@S@x2 zaso@u1~Zs>-1e7jV=0rwaILK2HPuqK0biJnhQZDrDx65~C0D_$_Z-Sxee>C&pM2S=2P9#eLq!#=>+ ziVCv50#Bv>>t@JEeD!fBjqPhJU^zmWD;ZA4wz=AwE>Wh&zZg}S58DuPM&N@|vR_!j zLaEMnlB_lonDG+?mWR%MT6dmLVi<+a>=yWTkakxt46lY{VDpLNhJPX1W&3@fR3{Nh z-2I^%+ouGU3akY|Gn`HVn9hC@_>`g%&H0k4U+Al4gtRL&19@R9LQ>*OL zg5ez1p#HKG#CTYJOnRk1#n4us)zI|~d^@j?386=8?fMVD!}%_mH@-1}=p9SabKk^^ zxyu7A#^Zg26Jol#^RG9J)o&J=m80^>0xLPXA;g25uYRNvogMt7?2>J}O?*~ITTOqA zXYBXwR5k3#x!lnX3Eb|pyPPbr8gF^pMNQRYI#b$=`rezPq6$As85BMG@wMU0TdL>X z*JdowaKhPW4<7XHVq7lpeu%De=o9Q*4XC-%y!d!1)Sk_s6tL96IdG2;YzMwnx2aU) z1;cn#fA_%mjW5p#yle!!Z^-l*l$8Kh!P(^)5Y(&g+Bsi_05Kc{2?6i%~6+Aq~u zF9goD0T~)!Uw&_3sn+S!q5g`SsURUfYqZwi?_*=APer%=>Pu>bJLSOAK`=>2Cip;i ze7-?baFh)1guyhDuz%jQGlRx1s`!^mk_)8}e7~8TgPF(Ghcx`5xOmio%9I#S zS@~$1YOMRlBPCC77uo)jfz`+U(Z=;Cr%$M|k8l-Cs`F9%R68yf7-$*SbR~9$w*Rt% z*L*xrE-%03j+we_Mp`|hvBsrgEMQrI#M0r?lyZXKt&S~o#CWz3SYq_K7eA^s%Np?_w4m@%hSiy9>WPGU$P?i>zTNkgBC@VPIVf)id fC$Tom3itmHYB)R?wf> Date: Wed, 18 Mar 2020 10:15:31 +0100 Subject: [PATCH 020/119] Add 'funding' field to `package.json` This was introduced to `npm` recently and allows users of the ol package to e.g. type `npm fund ol` and our opencollective page opens in a browser. Just typing `npm fund` in a npm package will list the funding options of the dependencies of the current project. --- package.json | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/package.json b/package.json index 6b632827b9..71d43f81cb 100644 --- a/package.json +++ b/package.json @@ -35,6 +35,10 @@ "bugs": { "url": "https://github.com/openlayers/openlayers/issues" }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/openlayers" + }, "dependencies": { "elm-pep": "^1.0.4", "pbf": "3.2.1", From d5b3d27e628d1f6e487e127f14b507fe5598dad3 Mon Sep 17 00:00:00 2001 From: Jiri Lysek Date: Thu, 19 Mar 2020 13:02:53 +0100 Subject: [PATCH 021/119] parsing color from IconStyle in KML files --- src/ol/format/KML.js | 7 ++++++- test/spec/ol/format/kml.test.js | 31 +++++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+), 1 deletion(-) diff --git a/src/ol/format/KML.js b/src/ol/format/KML.js index d94a4c473b..e693a4e127 100644 --- a/src/ol/format/KML.js +++ b/src/ol/format/KML.js @@ -1171,6 +1171,7 @@ function readStyleMapValue(node, objectStack) { const ICON_STYLE_PARSERS = makeStructureNS( NAMESPACE_URIS, { 'Icon': makeObjectPropertySetter(readIcon), + 'color': makeObjectPropertySetter(readColor), 'heading': makeObjectPropertySetter(readDecimal), 'hotSpot': makeObjectPropertySetter(readVec2), 'scale': makeObjectPropertySetter(readScale) @@ -1252,6 +1253,9 @@ function iconStyleParser(node, objectStack) { let scale = /** @type {number|undefined} */ (object['scale']); + const color = /** @type {[number]|undefined} */ + (object['color']); + if (drawIcon) { if (src == DEFAULT_IMAGE_STYLE_SRC) { size = DEFAULT_IMAGE_STYLE_SIZE; @@ -1271,7 +1275,8 @@ function iconStyleParser(node, objectStack) { rotation: rotation, scale: scale, size: size, - src: src + src: src, + color: color }); styleObject['imageStyle'] = imageStyle; } else { diff --git a/test/spec/ol/format/kml.test.js b/test/spec/ol/format/kml.test.js index e1a248bb75..7adedfc2c8 100644 --- a/test/spec/ol/format/kml.test.js +++ b/test/spec/ol/format/kml.test.js @@ -1992,6 +1992,37 @@ describe('ol.format.KML', function() { expect(style.getZIndex()).to.be(undefined); }); + it('can read a feature\'s IconStyle and set color of image', () => { + const text = + '' + + ' ' + + ' ' + + ' ' + + ''; + const fs = format.readFeatures(text); + expect(fs).to.have.length(1); + const f = fs[0]; + expect(f).to.be.an(Feature); + const styleFunction = f.getStyleFunction(); + const styleArray = styleFunction(f, 0); + expect(styleArray).to.be.an(Array); + expect(styleArray).to.have.length(1); + const style = styleArray[0]; + expect(style).to.be.an(Style); + expect(style.getFill()).to.be(getDefaultFillStyle()); + expect(style.getStroke()).to.be(getDefaultStrokeStyle()); + const imageStyle = style.getImage(); + expect(imageStyle.getColor()).to.eql([0xFF, 0, 0, 0xFF / 255]); + }); + it('can read a feature\'s LabelStyle', function() { const text = '' + From 7bf44078e178bd5da25b31406e92edf631b7dc9e Mon Sep 17 00:00:00 2001 From: Jiri Lysek Date: Thu, 19 Mar 2020 13:32:02 +0100 Subject: [PATCH 022/119] fixed type comment --- src/ol/format/KML.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/format/KML.js b/src/ol/format/KML.js index e693a4e127..2833548651 100644 --- a/src/ol/format/KML.js +++ b/src/ol/format/KML.js @@ -1253,7 +1253,7 @@ function iconStyleParser(node, objectStack) { let scale = /** @type {number|undefined} */ (object['scale']); - const color = /** @type {[number]|undefined} */ + const color = /** @type {Array|undefined} */ (object['color']); if (drawIcon) { From f942c482d8486aa44b1b871427e943815f233342 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Sat, 21 Mar 2020 00:15:49 +0100 Subject: [PATCH 023/119] Svg icon needs imgSize to display in ie11 --- examples/icon-color.js | 1 + 1 file changed, 1 insertion(+) diff --git a/examples/icon-color.js b/examples/icon-color.js index e88e3d52b8..11b30dd50e 100644 --- a/examples/icon-color.js +++ b/examples/icon-color.js @@ -25,6 +25,7 @@ rome.setStyle(new Style({ image: new Icon({ color: '#8959A8', crossOrigin: 'anonymous', + imgSize: [20, 20], src: 'data/square.svg' }) })); From fbb0364ea518818e60619115b6a0177165c67f5d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Sat, 21 Mar 2020 00:16:46 +0100 Subject: [PATCH 024/119] Make Icon's color attribute work in ie11 --- examples/data/square.svg | 2 +- src/ol/style/IconImage.js | 30 +++++++++++++++++++++++++----- 2 files changed, 26 insertions(+), 6 deletions(-) diff --git a/examples/data/square.svg b/examples/data/square.svg index 0b7a912a53..e7a5e249f3 100644 --- a/examples/data/square.svg +++ b/examples/data/square.svg @@ -2,6 +2,6 @@ - + diff --git a/src/ol/style/IconImage.js b/src/ol/style/IconImage.js index d2361e5bb7..a9739a3ed6 100644 --- a/src/ol/style/IconImage.js +++ b/src/ol/style/IconImage.js @@ -85,15 +85,18 @@ class IconImage extends EventTarget { /** * @private + * @param {CanvasRenderingContext2D=} context A context with the image already drawn into. * @return {boolean} The image canvas is tainted. */ - isTainted_() { + isTainted_(context) { if (this.tainted_ === undefined && this.imageState_ === ImageState.LOADED) { - this.tainted_ = false; - const context = createCanvasContext2D(1, 1); - try { + if (!context) { + context = createCanvasContext2D(1, 1); context.drawImage(this.image_, 0, 0); + } + try { context.getImageData(0, 0, 1, 1); + this.tainted_ = false; } catch (e) { this.tainted_ = true; } @@ -203,7 +206,7 @@ class IconImage extends EventTarget { * @private */ replaceColor_() { - if (!this.color_ || this.isTainted_()) { + if (!this.color_) { return; } @@ -213,6 +216,23 @@ class IconImage extends EventTarget { const ctx = this.canvas_.getContext('2d'); ctx.drawImage(this.image_, 0, 0); + if (this.isTainted_(ctx)) { + // Internet explorer 11 marks canvas as tainted if the drawn image is a svg. + // This makes the getImageData function throw a SecurityError. + // The same effect can be achieved with the globalCompositionOperation but + // Internet Explorer 11 does not properly support the multiply operation. + // So this is only used as a fallback. It is still better than having no icon + // at all. + const c = this.color_; + ctx.globalCompositeOperation = 'multiply'; + ctx.fillStyle = 'rgb(' + c[0] + ',' + c[1] + ',' + c[2] + ')'; + ctx.fillRect(0, 0, this.image_.width, this.image_.height); + + ctx.globalCompositeOperation = 'destination-in'; + ctx.drawImage(this.image_, 0, 0); + return; + } + const imgData = ctx.getImageData(0, 0, this.image_.width, this.image_.height); const data = imgData.data; const r = this.color_[0] / 255.0; From 24f9e1c6ac1cc4acab976419c5fec4f16b2090a9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Sun, 22 Mar 2020 13:29:29 +0100 Subject: [PATCH 025/119] Update comment for the IconImage replaceColor_ method --- src/ol/style/IconImage.js | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/ol/style/IconImage.js b/src/ol/style/IconImage.js index a9739a3ed6..38ca4cda5c 100644 --- a/src/ol/style/IconImage.js +++ b/src/ol/style/IconImage.js @@ -217,10 +217,12 @@ class IconImage extends EventTarget { ctx.drawImage(this.image_, 0, 0); if (this.isTainted_(ctx)) { - // Internet explorer 11 marks canvas as tainted if the drawn image is a svg. - // This makes the getImageData function throw a SecurityError. - // The same effect can be achieved with the globalCompositionOperation but - // Internet Explorer 11 does not properly support the multiply operation. + // If reading from the canvas throws a SecurityError the same effect can be + // achieved with globalCompositeOperation. + // This could be used as the default, but it is not fully supported by all + // browsers. E. g. Internet Explorer 11 does not support the multiply + // operation and the resulting image shape will be completelly filled with + // the provided color. // So this is only used as a fallback. It is still better than having no icon // at all. const c = this.color_; From 52d840b35d1ca5978467d57b671f2c0d679cd18a Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 08:55:33 +0000 Subject: [PATCH 026/119] Bump marked from 0.8.0 to 0.8.2 Bumps [marked](https://github.com/markedjs/marked) from 0.8.0 to 0.8.2. - [Release notes](https://github.com/markedjs/marked/releases) - [Commits](https://github.com/markedjs/marked/compare/v0.8.0...v0.8.2) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 6 +++--- package.json | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..0f5b5d5726 100644 --- a/package-lock.json +++ b/package-lock.json @@ -7858,9 +7858,9 @@ "dev": true }, "marked": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/marked/-/marked-0.8.0.tgz", - "integrity": "sha512-MyUe+T/Pw4TZufHkzAfDj6HarCBWia2y27/bhuYkTaiUnfDYFnCP3KUN+9oM7Wi6JA2rymtVYbQu3spE0GCmxQ==", + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/marked/-/marked-0.8.2.tgz", + "integrity": "sha512-EGwzEeCcLniFX51DhTpmTom+dSA/MG/OBUDjnWtHbEnjAH180VzUeAw+oE4+Zv+CoYBWyRlYOTR0N8SO9R1PVw==", "dev": true }, "md5.js": { diff --git a/package.json b/package.json index 71d43f81cb..60257ed2fe 100644 --- a/package.json +++ b/package.json @@ -81,7 +81,7 @@ "karma-sourcemap-loader": "^0.3.7", "karma-webpack": "^4.0.0-rc.2", "loglevelnext": "^3.0.1", - "marked": "0.8.0", + "marked": "0.8.2", "mocha": "7.1.0", "ol-mapbox-style": "^6.0.0", "pixelmatch": "^5.1.0", From bbc88708329e4209ede85170e0f62da5cb7738bd Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 08:57:18 +0000 Subject: [PATCH 027/119] Bump babel-loader from 8.0.6 to 8.1.0 Bumps [babel-loader](https://github.com/babel/babel-loader) from 8.0.6 to 8.1.0. - [Release notes](https://github.com/babel/babel-loader/releases) - [Changelog](https://github.com/babel/babel-loader/blob/master/CHANGELOG.md) - [Commits](https://github.com/babel/babel-loader/compare/v8.0.6...v8.1.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 83 +++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 76 insertions(+), 7 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..29fe2e818f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2343,15 +2343,84 @@ } }, "babel-loader": { - "version": "8.0.6", - "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-8.0.6.tgz", - "integrity": "sha512-4BmWKtBOBm13uoUwd08UwjZlaw3O9GWf456R9j+5YykFZ6LUIjIKLc0zEZf+hauxPOJs96C8k6FvYD09vWzhYw==", + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-8.1.0.tgz", + "integrity": "sha512-7q7nC1tYOrqvUrN3LQK4GwSk/TQorZSOlO9C+RZDZpODgyN4ZlCqE5q9cDsyWOliN+aU9B4JX01xK9eJXowJLw==", "dev": true, "requires": { - "find-cache-dir": "^2.0.0", - "loader-utils": "^1.0.2", - "mkdirp": "^0.5.1", - "pify": "^4.0.1" + "find-cache-dir": "^2.1.0", + "loader-utils": "^1.4.0", + "mkdirp": "^0.5.3", + "pify": "^4.0.1", + "schema-utils": "^2.6.5" + }, + "dependencies": { + "ajv": { + "version": "6.12.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.0.tgz", + "integrity": "sha512-D6gFiFA0RRLyUbvijN74DWAjXSFxWKaWP7mldxkVhyhAV3+SWA9HEJPHQ2c9soIeTFJqcSdFDGFgdqs1iUU2Hw==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "ajv-keywords": { + "version": "3.4.1", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.4.1.tgz", + "integrity": "sha512-RO1ibKvd27e6FEShVFfPALuHI3WjSVNeK5FIsmme/LYRNxjKuNj+Dt7bucLa6NdSv3JcVTyMlm9kGR84z1XpaQ==", + "dev": true + }, + "emojis-list": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", + "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", + "dev": true + }, + "fast-deep-equal": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.1.tgz", + "integrity": "sha512-8UEa58QDLauDNfpbrX55Q9jrGHThw2ZMdOky5Gl1CDtVeJDPVrG4Jxx1N8jw2gkWaff5UUuX1KJd+9zGe2B+ZA==", + "dev": true + }, + "loader-utils": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.4.0.tgz", + "integrity": "sha512-qH0WSMBtn/oHuwjy/NucEgbx5dbxxnxup9s4PVXJUDHZBQY+s0NWA9rJf53RBnQZxfch7euUui7hpoAPvALZdA==", + "dev": true, + "requires": { + "big.js": "^5.2.2", + "emojis-list": "^3.0.0", + "json5": "^1.0.1" + } + }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "mkdirp": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.3.tgz", + "integrity": "sha512-P+2gwrFqx8lhew375MQHHeTlY8AuOJSrGf0R5ddkEndUkmwpgUob/vQuBD1V22/Cw1/lJr4x+EjllSezBThzBg==", + "dev": true, + "requires": { + "minimist": "^1.2.5" + } + }, + "schema-utils": { + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.6.5.tgz", + "integrity": "sha512-5KXuwKziQrTVHh8j/Uxz+QUbxkaLW9X/86NBlx/gnKgtsZA2GIVMUn17qWhRFwF8jdYb3Dig5hRO/W5mZqy6SQ==", + "dev": true, + "requires": { + "ajv": "^6.12.0", + "ajv-keywords": "^3.4.1" + } + } } }, "babel-messages": { From d8b2e452d5ac5a17dbc40d13beaed492c81f3285 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 08:58:20 +0000 Subject: [PATCH 028/119] Bump @babel/core from 7.8.7 to 7.9.0 Bumps [@babel/core](https://github.com/babel/babel) from 7.8.7 to 7.9.0. - [Release notes](https://github.com/babel/babel/releases) - [Changelog](https://github.com/babel/babel/blob/master/CHANGELOG.md) - [Commits](https://github.com/babel/babel/compare/v7.8.7...v7.9.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 185 +++++++++++++++++++++++++++++++++++----------- 1 file changed, 140 insertions(+), 45 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..934f710447 100644 --- a/package-lock.json +++ b/package-lock.json @@ -25,22 +25,23 @@ } }, "@babel/core": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.8.7.tgz", - "integrity": "sha512-rBlqF3Yko9cynC5CCFy6+K/w2N+Sq/ff2BPy+Krp7rHlABIr5epbA7OxVeKoMHB39LZOp1UY5SuLjy6uWi35yA==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.9.0.tgz", + "integrity": "sha512-kWc7L0fw1xwvI0zi8OKVBuxRVefwGOrKSQMvrQ3dW+bIIavBY3/NpXmpjMy7bQnLgwgzWQZ8TlM57YHpHNHz4w==", "dev": true, "requires": { "@babel/code-frame": "^7.8.3", - "@babel/generator": "^7.8.7", - "@babel/helpers": "^7.8.4", - "@babel/parser": "^7.8.7", + "@babel/generator": "^7.9.0", + "@babel/helper-module-transforms": "^7.9.0", + "@babel/helpers": "^7.9.0", + "@babel/parser": "^7.9.0", "@babel/template": "^7.8.6", - "@babel/traverse": "^7.8.6", - "@babel/types": "^7.8.7", + "@babel/traverse": "^7.9.0", + "@babel/types": "^7.9.0", "convert-source-map": "^1.7.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.1", - "json5": "^2.1.0", + "json5": "^2.1.2", "lodash": "^4.17.13", "resolve": "^1.3.2", "semver": "^5.4.1", @@ -57,32 +58,47 @@ } }, "@babel/generator": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.8.7.tgz", - "integrity": "sha512-DQwjiKJqH4C3qGiyQCAExJHoZssn49JTMJgZ8SANGgVFdkupcUhLOdkAeoC6kmHZCPfoDG5M0b6cFlSN5wW7Ew==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.9.3.tgz", + "integrity": "sha512-RpxM252EYsz9qLUIq6F7YJyK1sv0wWDBFuztfDGWaQKzHjqDHysxSiRUpA/X9jmfqo+WzkAVKFaUily5h+gDCQ==", "dev": true, "requires": { - "@babel/types": "^7.8.7", + "@babel/types": "^7.9.0", "jsesc": "^2.5.1", "lodash": "^4.17.13", "source-map": "^0.5.0" } }, - "@babel/highlight": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.8.3.tgz", - "integrity": "sha512-PX4y5xQUvy0fnEVHrYOarRPXVWafSjTW9T0Hab8gVIawpl2Sj0ORyrygANq+KjcNlSSTw0YCLSNA8OyZ1I4yEg==", + "@babel/helper-module-transforms": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.9.0.tgz", + "integrity": "sha512-0FvKyu0gpPfIQ8EkxlrAydOWROdHpBmiCiRwLkUiBGhCUPRRbVD2/tm3sFr/c/GWFrQ/ffutGUAnx7V0FzT2wA==", "dev": true, "requires": { + "@babel/helper-module-imports": "^7.8.3", + "@babel/helper-replace-supers": "^7.8.6", + "@babel/helper-simple-access": "^7.8.3", + "@babel/helper-split-export-declaration": "^7.8.3", + "@babel/template": "^7.8.6", + "@babel/types": "^7.9.0", + "lodash": "^4.17.13" + } + }, + "@babel/highlight": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.9.0.tgz", + "integrity": "sha512-lJZPilxX7Op3Nv/2cvFdnlepPXDxi29wxteT57Q965oc5R9v86ztx0jfxVrTcBk8C2kcPkkDa2Z4T3ZsPPVWsQ==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.9.0", "chalk": "^2.0.0", - "esutils": "^2.0.2", "js-tokens": "^4.0.0" } }, "@babel/parser": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.8.7.tgz", - "integrity": "sha512-9JWls8WilDXFGxs0phaXAZgpxTZhSk/yOYH2hTHC0X1yC7Z78IJfvR1vJ+rmJKq3I35td2XzXzN6ZLYlna+r/A==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.9.3.tgz", + "integrity": "sha512-E6SpIDJZ0cZAKoCNk+qSDd0ChfTnpiJN9FfNf3RZ20dzwA2vL2oq5IX1XTVT+4vDmRlta2nGk5HGMMskJAR+4A==", "dev": true }, "@babel/template": { @@ -97,29 +113,29 @@ } }, "@babel/traverse": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.8.6.tgz", - "integrity": "sha512-2B8l0db/DPi8iinITKuo7cbPznLCEk0kCxDoB9/N6gGNg/gxOXiR/IcymAFPiBwk5w6TtQ27w4wpElgp9btR9A==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.9.0.tgz", + "integrity": "sha512-jAZQj0+kn4WTHO5dUZkZKhbFrqZE7K5LAQ5JysMnmvGij+wOdr+8lWqPeW0BcF4wFwrEXXtdGO7wcV6YPJcf3w==", "dev": true, "requires": { "@babel/code-frame": "^7.8.3", - "@babel/generator": "^7.8.6", + "@babel/generator": "^7.9.0", "@babel/helper-function-name": "^7.8.3", "@babel/helper-split-export-declaration": "^7.8.3", - "@babel/parser": "^7.8.6", - "@babel/types": "^7.8.6", + "@babel/parser": "^7.9.0", + "@babel/types": "^7.9.0", "debug": "^4.1.0", "globals": "^11.1.0", "lodash": "^4.17.13" } }, "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -140,14 +156,20 @@ "dev": true }, "json5": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.1.1.tgz", - "integrity": "sha512-l+3HXD0GEI3huGq1njuqtzYK8OYJyXMkOLtQ53pjWh89tvWS2h6l+1zMkYWqlb57+SiQodKZyvMEFb2X+KrFhQ==", + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.1.2.tgz", + "integrity": "sha512-MoUOQ4WdiN3yxhm7NEVJSJrieAo5hNSLQ5sj05OTRHPL9HOBy8u4Bu88jsC1jvqAdN+E1bJmsUcZH+1HQxliqQ==", "dev": true, "requires": { - "minimist": "^1.2.0" + "minimist": "^1.2.5" } }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, "source-map": { "version": "0.5.7", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", @@ -744,6 +766,12 @@ } } }, + "@babel/helper-validator-identifier": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.9.0.tgz", + "integrity": "sha512-6G8bQKjOh+of4PV/ThDm/rRqlU7+IGoJuofpagU5GlEl29Vv0RGqqt86ZGRV8ZuSOY3o+8yXl5y782SMcG7SHw==", + "dev": true + }, "@babel/helper-wrap-function": { "version": "7.8.3", "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.8.3.tgz", @@ -770,26 +798,93 @@ } }, "@babel/helpers": { - "version": "7.8.4", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.8.4.tgz", - "integrity": "sha512-VPbe7wcQ4chu4TDQjimHv/5tj73qz88o12EPkO2ValS2QiQS/1F2SsjyIGNnAD0vF/nZS6Cf9i+vW6HIlnaR8w==", + "version": "7.9.2", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.9.2.tgz", + "integrity": "sha512-JwLvzlXVPjO8eU9c/wF9/zOIN7X6h8DYf7mG4CiFRZRvZNKEF5dQ3H3V+ASkHoIB3mWhatgl5ONhyqHRI6MppA==", "dev": true, "requires": { "@babel/template": "^7.8.3", - "@babel/traverse": "^7.8.4", - "@babel/types": "^7.8.3" + "@babel/traverse": "^7.9.0", + "@babel/types": "^7.9.0" }, "dependencies": { - "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "@babel/code-frame": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.8.3.tgz", + "integrity": "sha512-a9gxpmdXtZEInkCSHUJDLHZVBgb1QS0jhss4cPP93EW7s+uC5bikET2twEF3KV+7rDblJcmNvTR7VJejqd2C2g==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/highlight": "^7.8.3" + } + }, + "@babel/generator": { + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.9.3.tgz", + "integrity": "sha512-RpxM252EYsz9qLUIq6F7YJyK1sv0wWDBFuztfDGWaQKzHjqDHysxSiRUpA/X9jmfqo+WzkAVKFaUily5h+gDCQ==", + "dev": true, + "requires": { + "@babel/types": "^7.9.0", + "jsesc": "^2.5.1", + "lodash": "^4.17.13", + "source-map": "^0.5.0" + } + }, + "@babel/highlight": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.9.0.tgz", + "integrity": "sha512-lJZPilxX7Op3Nv/2cvFdnlepPXDxi29wxteT57Q965oc5R9v86ztx0jfxVrTcBk8C2kcPkkDa2Z4T3ZsPPVWsQ==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.9.0", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + } + }, + "@babel/parser": { + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.9.3.tgz", + "integrity": "sha512-E6SpIDJZ0cZAKoCNk+qSDd0ChfTnpiJN9FfNf3RZ20dzwA2vL2oq5IX1XTVT+4vDmRlta2nGk5HGMMskJAR+4A==", + "dev": true + }, + "@babel/traverse": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.9.0.tgz", + "integrity": "sha512-jAZQj0+kn4WTHO5dUZkZKhbFrqZE7K5LAQ5JysMnmvGij+wOdr+8lWqPeW0BcF4wFwrEXXtdGO7wcV6YPJcf3w==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.8.3", + "@babel/generator": "^7.9.0", + "@babel/helper-function-name": "^7.8.3", + "@babel/helper-split-export-declaration": "^7.8.3", + "@babel/parser": "^7.9.0", + "@babel/types": "^7.9.0", + "debug": "^4.1.0", + "globals": "^11.1.0", + "lodash": "^4.17.13" + } + }, + "@babel/types": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } + }, + "jsesc": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", + "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", + "dev": true + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true } } }, From 5ab7f5dacf171b982f56d6c9cd47295ce36e8ce0 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 08:59:43 +0000 Subject: [PATCH 029/119] Bump fs-extra from 8.1.0 to 9.0.0 Bumps [fs-extra](https://github.com/jprichardson/node-fs-extra) from 8.1.0 to 9.0.0. - [Release notes](https://github.com/jprichardson/node-fs-extra/releases) - [Changelog](https://github.com/jprichardson/node-fs-extra/blob/master/CHANGELOG.md) - [Commits](https://github.com/jprichardson/node-fs-extra/compare/8.1.0...9.0.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 33 ++++++++++++++++++++++++++++----- package.json | 2 +- 2 files changed, 29 insertions(+), 6 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..714d891597 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2235,6 +2235,12 @@ "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", "dev": true }, + "at-least-node": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", + "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", + "dev": true + }, "atob": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", @@ -5277,14 +5283,15 @@ } }, "fs-extra": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-8.1.0.tgz", - "integrity": "sha512-yhlQgA6mnOJUKOsRUFsgJdQCvkKhcz8tlZG5HBQfReYZy46OwLcY+Zia0mtdHsOo9y/hP+CxMN0TU9QxoOtG4g==", + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.0.0.tgz", + "integrity": "sha512-pmEYSk3vYsG/bF651KPUXZ+hvjpgWYw/Gc7W9NFUe3ZVLczKKWIij3IKpOrQcdw4TILtibFslZ0UmR8Vvzig4g==", "dev": true, "requires": { + "at-least-node": "^1.0.0", "graceful-fs": "^4.2.0", - "jsonfile": "^4.0.0", - "universalify": "^0.1.0" + "jsonfile": "^6.0.1", + "universalify": "^1.0.0" }, "dependencies": { "graceful-fs": { @@ -5292,6 +5299,22 @@ "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.3.tgz", "integrity": "sha512-a30VEBm4PEdx1dRB7MFK7BejejvCvBronbLjht+sHuGYj8PHs7M/5Z+rt5lw551vZ7yfTCj4Vuyy3mSJytDWRQ==", "dev": true + }, + "jsonfile": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.0.1.tgz", + "integrity": "sha512-jR2b5v7d2vIOust+w3wtFKZIfpC2pnRmFAhAC/BuweZFQR8qZzxH1OyrQ10HmdVYiXWkYUqPVsz91cG7EL2FBg==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.6", + "universalify": "^1.0.0" + } + }, + "universalify": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-1.0.0.tgz", + "integrity": "sha512-rb6X1W158d7pRQBg5gkR8uPaSfiids68LTJQYOtEUhoJUWBdaQHsuT/EUduxXYxcrt4r5PJ4fuHW1MHT6p0qug==", + "dev": true } } }, diff --git a/package.json b/package.json index 71d43f81cb..a51b249c8d 100644 --- a/package.json +++ b/package.json @@ -64,7 +64,7 @@ "eslint-config-openlayers": "^13.0.0", "expect.js": "0.3.1", "front-matter": "^3.0.2", - "fs-extra": "^8.0.0", + "fs-extra": "^9.0.0", "glob": "^7.1.5", "globby": "^11.0.0", "handlebars": "4.7.3", From 274135db2e24dc563daa0a1a20449b017e64d497 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 09:00:00 +0000 Subject: [PATCH 030/119] Bump rollup from 1.32.1 to 2.1.0 Bumps [rollup](https://github.com/rollup/rollup) from 1.32.1 to 2.1.0. - [Release notes](https://github.com/rollup/rollup/releases) - [Changelog](https://github.com/rollup/rollup/blob/master/CHANGELOG.md) - [Commits](https://github.com/rollup/rollup/compare/v1.32.1...v2.1.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 21 ++++++++++----------- package.json | 2 +- 2 files changed, 11 insertions(+), 12 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..d50fd4ca8f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9942,21 +9942,20 @@ } }, "rollup": { - "version": "1.32.1", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-1.32.1.tgz", - "integrity": "sha512-/2HA0Ec70TvQnXdzynFffkjA6XN+1e2pEv/uKS5Ulca40g2L7KuOE3riasHoNVHOsFD5KKZgDsMk1CP3Tw9s+A==", + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.1.0.tgz", + "integrity": "sha512-gfE1455AEazVVTJoeQtcOq/U6GSxwoj4XPSWVsuWmgIxj7sBQNLDOSA82PbdMe+cP8ql8fR1jogPFe8Wg8g4SQ==", "dev": true, "requires": { - "@types/estree": "*", - "@types/node": "*", - "acorn": "^7.1.0" + "fsevents": "~2.1.2" }, "dependencies": { - "acorn": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.1.1.tgz", - "integrity": "sha512-add7dgA5ppRPxCFJoAGfMDi7PIBXq1RtGo7BhbLaxwrXPOmw8gq48Y9ozT01hUKy9byMjlR20EJhu5zlkErEkg==", - "dev": true + "fsevents": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.1.2.tgz", + "integrity": "sha512-R4wDiBwZ0KzpgOWetKDug1FZcYhqYnUYKtfZYt4mD5SBz76q0KR4Q9o7GIPamsVPGmW3EYPPJ0dOOjvx32ldZA==", + "dev": true, + "optional": true } } }, diff --git a/package.json b/package.json index 71d43f81cb..31367c5895 100644 --- a/package.json +++ b/package.json @@ -88,7 +88,7 @@ "pngjs": "^3.4.0", "proj4": "2.6.0", "puppeteer": "~2.1.0", - "rollup": "^1.25.1", + "rollup": "^2.1.0", "rollup-plugin-babel": "^4.3.3", "rollup-plugin-commonjs": "^10.0.0", "rollup-plugin-node-resolve": "^5.2.0", From 7dd6bb7c1ba9f782e104d30725506afeb43977b4 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 09:01:12 +0000 Subject: [PATCH 031/119] Bump @babel/preset-env from 7.8.7 to 7.9.0 Bumps [@babel/preset-env](https://github.com/babel/babel) from 7.8.7 to 7.9.0. - [Release notes](https://github.com/babel/babel/releases) - [Changelog](https://github.com/babel/babel/blob/master/CHANGELOG.md) - [Commits](https://github.com/babel/babel/compare/v7.8.7...v7.9.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 485 +++++++++++++++++++++++----------------------- 1 file changed, 246 insertions(+), 239 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..00177091dd 100644 --- a/package-lock.json +++ b/package-lock.json @@ -14,12 +14,12 @@ } }, "@babel/compat-data": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.8.6.tgz", - "integrity": "sha512-CurCIKPTkS25Mb8mz267vU95vy+TyUpnctEX2lV33xWNmHAfjruztgiPBbXZRh3xZZy1CYvGx6XfxyTVS+sk7Q==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.9.0.tgz", + "integrity": "sha512-zeFQrr+284Ekvd9e7KAX954LkapWiOmQtsfHirhxqfdlX6MEC32iRE+pqUGlYIBchdevaCwvzxWGSy/YBNI85g==", "dev": true, "requires": { - "browserslist": "^4.8.5", + "browserslist": "^4.9.1", "invariant": "^2.2.4", "semver": "^5.5.0" } @@ -203,12 +203,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -226,36 +226,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", - "lodash": "^4.17.13", - "to-fast-properties": "^2.0.0" - } - } - } - }, - "@babel/helper-call-delegate": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/helper-call-delegate/-/helper-call-delegate-7.8.7.tgz", - "integrity": "sha512-doAA5LAKhsFCR0LAFIf+r2RSMmC+m8f/oQ+URnUET/rWeEzC0yTRmAGyWkD4sSu3xwbS7MYQ2u+xlt1V5R56KQ==", - "dev": true, - "requires": { - "@babel/helper-hoist-variables": "^7.8.3", - "@babel/traverse": "^7.8.3", - "@babel/types": "^7.8.7" - }, - "dependencies": { - "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", - "dev": true, - "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -276,38 +252,59 @@ } }, "@babel/helper-create-regexp-features-plugin": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.8.6.tgz", - "integrity": "sha512-bPyujWfsHhV/ztUkwGHz/RPV1T1TDEsSZDsN42JPehndA+p1KKTh3npvTadux0ZhCrytx9tvjpWNowKby3tM6A==", + "version": "7.8.8", + "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.8.8.tgz", + "integrity": "sha512-LYVPdwkrQEiX9+1R29Ld/wTrmQu1SSKYnuOk3g0CkcZMA1p0gsNxJFj/3gBdaJ7Cg0Fnek5z0DsMULePP7Lrqg==", "dev": true, "requires": { "@babel/helper-annotate-as-pure": "^7.8.3", "@babel/helper-regex": "^7.8.3", - "regexpu-core": "^4.6.0" + "regexpu-core": "^4.7.0" }, "dependencies": { "regenerate-unicode-properties": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-8.1.0.tgz", - "integrity": "sha512-LGZzkgtLY79GeXLm8Dp0BVLdQlWICzBnJz/ipWUgo59qBaZ+BHtq51P2q1uVZlppMuUAT37SDk39qUbjTWB7bA==", + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-8.2.0.tgz", + "integrity": "sha512-F9DjY1vKLo/tPePDycuH3dn9H1OTPIkVD9Kz4LODu+F2C75mgjAJ7x/gwy6ZcSNRAAkhNlJSOHRe8k3p+K9WhA==", "dev": true, "requires": { "regenerate": "^1.4.0" } }, "regexpu-core": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-4.6.0.tgz", - "integrity": "sha512-YlVaefl8P5BnFYOITTNzDvan1ulLOiXJzCNZxduTIosN17b87h3bvG9yHMoHaRuo88H4mQ06Aodj5VtYGGGiTg==", + "version": "4.7.0", + "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-4.7.0.tgz", + "integrity": "sha512-TQ4KXRnIn6tz6tjnrXEkD/sshygKH/j5KzK86X8MkeHyZ8qst/LZ89j3X4/8HEIfHANTFIP/AbXakeRhWIl5YQ==", "dev": true, "requires": { "regenerate": "^1.4.0", - "regenerate-unicode-properties": "^8.1.0", - "regjsgen": "^0.5.0", - "regjsparser": "^0.6.0", + "regenerate-unicode-properties": "^8.2.0", + "regjsgen": "^0.5.1", + "regjsparser": "^0.6.4", "unicode-match-property-ecmascript": "^1.0.4", - "unicode-match-property-value-ecmascript": "^1.1.0" + "unicode-match-property-value-ecmascript": "^1.2.0" } + }, + "regjsgen": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.5.1.tgz", + "integrity": "sha512-5qxzGZjDs9w4tzT3TPhCJqWdCc3RLYwy9J2NB0nm5Lz+S273lvWcpjaTGHsT1dc6Hhfq41uSEOw8wBmxrKOuyg==", + "dev": true + }, + "regjsparser": { + "version": "0.6.4", + "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.6.4.tgz", + "integrity": "sha512-64O87/dPDgfk8/RQqC4gkZoGyyWFIEUTTh80CU6CWuK5vkCGyekIx+oKcEIYtP/RAxSQltCZHCNu/mdd7fqlJw==", + "dev": true, + "requires": { + "jsesc": "~0.5.0" + } + }, + "unicode-match-property-value-ecmascript": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-1.2.0.tgz", + "integrity": "sha512-wjuQHGQVofmSJv1uVISKLE5zO2rNGzM/KCYZch/QQvez7C1hUhBIuZ701fYXExuufJFMPhv2SyL8CyoIfMLbIQ==", + "dev": true } } }, @@ -323,12 +320,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -346,12 +343,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -414,12 +411,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -436,12 +433,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -471,9 +468,9 @@ } }, "@babel/helper-module-transforms": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.8.6.tgz", - "integrity": "sha512-RDnGJSR5EFBJjG3deY0NiL0K9TO8SXxS9n/MPsbPK/s9LbQymuLNtlzvDiNS7IpecuL45cMeLVkA+HfmlrnkRg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.9.0.tgz", + "integrity": "sha512-0FvKyu0gpPfIQ8EkxlrAydOWROdHpBmiCiRwLkUiBGhCUPRRbVD2/tm3sFr/c/GWFrQ/ffutGUAnx7V0FzT2wA==", "dev": true, "requires": { "@babel/helper-module-imports": "^7.8.3", @@ -481,7 +478,7 @@ "@babel/helper-simple-access": "^7.8.3", "@babel/helper-split-export-declaration": "^7.8.3", "@babel/template": "^7.8.6", - "@babel/types": "^7.8.6", + "@babel/types": "^7.9.0", "lodash": "^4.17.13" }, "dependencies": { @@ -494,30 +491,21 @@ "@babel/highlight": "^7.8.3" } }, - "@babel/helper-module-imports": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.8.3.tgz", - "integrity": "sha512-R0Bx3jippsbAEtzkpZ/6FIiuzOURPcMjHp+Z6xPe6DtApDJx+w7UYyOLanZqO8+wKR9G10s/FmHXvxaMd9s6Kg==", - "dev": true, - "requires": { - "@babel/types": "^7.8.3" - } - }, "@babel/highlight": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.8.3.tgz", - "integrity": "sha512-PX4y5xQUvy0fnEVHrYOarRPXVWafSjTW9T0Hab8gVIawpl2Sj0ORyrygANq+KjcNlSSTw0YCLSNA8OyZ1I4yEg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.9.0.tgz", + "integrity": "sha512-lJZPilxX7Op3Nv/2cvFdnlepPXDxi29wxteT57Q965oc5R9v86ztx0jfxVrTcBk8C2kcPkkDa2Z4T3ZsPPVWsQ==", "dev": true, "requires": { + "@babel/helper-validator-identifier": "^7.9.0", "chalk": "^2.0.0", - "esutils": "^2.0.2", "js-tokens": "^4.0.0" } }, "@babel/parser": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.8.7.tgz", - "integrity": "sha512-9JWls8WilDXFGxs0phaXAZgpxTZhSk/yOYH2hTHC0X1yC7Z78IJfvR1vJ+rmJKq3I35td2XzXzN6ZLYlna+r/A==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.9.3.tgz", + "integrity": "sha512-E6SpIDJZ0cZAKoCNk+qSDd0ChfTnpiJN9FfNf3RZ20dzwA2vL2oq5IX1XTVT+4vDmRlta2nGk5HGMMskJAR+4A==", "dev": true }, "@babel/template": { @@ -532,12 +520,12 @@ } }, "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -554,12 +542,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -595,12 +583,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -629,58 +617,58 @@ } }, "@babel/generator": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.8.7.tgz", - "integrity": "sha512-DQwjiKJqH4C3qGiyQCAExJHoZssn49JTMJgZ8SANGgVFdkupcUhLOdkAeoC6kmHZCPfoDG5M0b6cFlSN5wW7Ew==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.9.3.tgz", + "integrity": "sha512-RpxM252EYsz9qLUIq6F7YJyK1sv0wWDBFuztfDGWaQKzHjqDHysxSiRUpA/X9jmfqo+WzkAVKFaUily5h+gDCQ==", "dev": true, "requires": { - "@babel/types": "^7.8.7", + "@babel/types": "^7.9.0", "jsesc": "^2.5.1", "lodash": "^4.17.13", "source-map": "^0.5.0" } }, "@babel/highlight": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.8.3.tgz", - "integrity": "sha512-PX4y5xQUvy0fnEVHrYOarRPXVWafSjTW9T0Hab8gVIawpl2Sj0ORyrygANq+KjcNlSSTw0YCLSNA8OyZ1I4yEg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.9.0.tgz", + "integrity": "sha512-lJZPilxX7Op3Nv/2cvFdnlepPXDxi29wxteT57Q965oc5R9v86ztx0jfxVrTcBk8C2kcPkkDa2Z4T3ZsPPVWsQ==", "dev": true, "requires": { + "@babel/helper-validator-identifier": "^7.9.0", "chalk": "^2.0.0", - "esutils": "^2.0.2", "js-tokens": "^4.0.0" } }, "@babel/parser": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.8.7.tgz", - "integrity": "sha512-9JWls8WilDXFGxs0phaXAZgpxTZhSk/yOYH2hTHC0X1yC7Z78IJfvR1vJ+rmJKq3I35td2XzXzN6ZLYlna+r/A==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.9.3.tgz", + "integrity": "sha512-E6SpIDJZ0cZAKoCNk+qSDd0ChfTnpiJN9FfNf3RZ20dzwA2vL2oq5IX1XTVT+4vDmRlta2nGk5HGMMskJAR+4A==", "dev": true }, "@babel/traverse": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.8.6.tgz", - "integrity": "sha512-2B8l0db/DPi8iinITKuo7cbPznLCEk0kCxDoB9/N6gGNg/gxOXiR/IcymAFPiBwk5w6TtQ27w4wpElgp9btR9A==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.9.0.tgz", + "integrity": "sha512-jAZQj0+kn4WTHO5dUZkZKhbFrqZE7K5LAQ5JysMnmvGij+wOdr+8lWqPeW0BcF4wFwrEXXtdGO7wcV6YPJcf3w==", "dev": true, "requires": { "@babel/code-frame": "^7.8.3", - "@babel/generator": "^7.8.6", + "@babel/generator": "^7.9.0", "@babel/helper-function-name": "^7.8.3", "@babel/helper-split-export-declaration": "^7.8.3", - "@babel/parser": "^7.8.6", - "@babel/types": "^7.8.6", + "@babel/parser": "^7.9.0", + "@babel/types": "^7.9.0", "debug": "^4.1.0", "globals": "^11.1.0", "lodash": "^4.17.13" } }, "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -710,12 +698,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -744,6 +732,12 @@ } } }, + "@babel/helper-validator-identifier": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.9.0.tgz", + "integrity": "sha512-6G8bQKjOh+of4PV/ThDm/rRqlU7+IGoJuofpagU5GlEl29Vv0RGqqt86ZGRV8ZuSOY3o+8yXl5y782SMcG7SHw==", + "dev": true + }, "@babel/helper-wrap-function": { "version": "7.8.3", "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.8.3.tgz", @@ -757,12 +751,12 @@ }, "dependencies": { "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } @@ -851,10 +845,20 @@ "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.0" } }, - "@babel/plugin-proposal-object-rest-spread": { + "@babel/plugin-proposal-numeric-separator": { "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.8.3.tgz", - "integrity": "sha512-8qvuPwU/xxUCt78HocNlv0mXXo0wdh9VT1R04WU8HGOfaOob26pF+9P5/lYjN/q7DHOX1bvX60hnhOvuQUJdbA==", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-numeric-separator/-/plugin-proposal-numeric-separator-7.8.3.tgz", + "integrity": "sha512-jWioO1s6R/R+wEHizfaScNsAx+xKgwTLNXSh7tTC4Usj3ItsPEhYkEpU4h+lpnBwq7NBVOJXfO6cRFYcX69JUQ==", + "dev": true, + "requires": { + "@babel/helper-plugin-utils": "^7.8.3", + "@babel/plugin-syntax-numeric-separator": "^7.8.3" + } + }, + "@babel/plugin-proposal-object-rest-spread": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.9.0.tgz", + "integrity": "sha512-UgqBv6bjq4fDb8uku9f+wcm1J7YxJ5nT7WO/jBr0cl0PLKb7t1O6RNR1kZbjgx2LQtsDI9hwoQVmn0yhXeQyow==", "dev": true, "requires": { "@babel/helper-plugin-utils": "^7.8.3", @@ -872,9 +876,9 @@ } }, "@babel/plugin-proposal-optional-chaining": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.8.3.tgz", - "integrity": "sha512-QIoIR9abkVn+seDE3OjA08jWcs3eZ9+wJCKSRgo3WdEU2csFYgdScb+8qHB3+WXsGJD55u+5hWCISI7ejXS+kg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.9.0.tgz", + "integrity": "sha512-NDn5tu3tcv4W30jNhmc2hyD5c56G6cXx4TesJubhxrJeCvuuMpttxr0OnNCqbZGhFjLrg+NIhxxC+BK5F6yS3w==", "dev": true, "requires": { "@babel/helper-plugin-utils": "^7.8.3", @@ -882,12 +886,12 @@ } }, "@babel/plugin-proposal-unicode-property-regex": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-unicode-property-regex/-/plugin-proposal-unicode-property-regex-7.8.3.tgz", - "integrity": "sha512-1/1/rEZv2XGweRwwSkLpY+s60za9OZ1hJs4YDqFHCw0kYWYwL5IFljVY1MYBL+weT1l9pokDO2uhSTLVxzoHkQ==", + "version": "7.8.8", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-unicode-property-regex/-/plugin-proposal-unicode-property-regex-7.8.8.tgz", + "integrity": "sha512-EVhjVsMpbhLw9ZfHWSx2iy13Q8Z/eg8e8ccVWt23sWQK5l1UdkoLJPN5w69UA4uITGBnEZD2JOe4QOHycYKv8A==", "dev": true, "requires": { - "@babel/helper-create-regexp-features-plugin": "^7.8.3", + "@babel/helper-create-regexp-features-plugin": "^7.8.8", "@babel/helper-plugin-utils": "^7.8.3" } }, @@ -927,6 +931,15 @@ "@babel/helper-plugin-utils": "^7.8.0" } }, + "@babel/plugin-syntax-numeric-separator": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.8.3.tgz", + "integrity": "sha512-H7dCMAdN83PcCmqmkHB5dtp+Xa9a6LKSvA2hiFBC/5alSHxM5VgWZXFqDi0YFe8XNGT6iCa+z4V4zSt/PdZ7Dw==", + "dev": true, + "requires": { + "@babel/helper-plugin-utils": "^7.8.3" + } + }, "@babel/plugin-syntax-object-rest-spread": { "version": "7.8.3", "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz", @@ -981,28 +994,6 @@ "@babel/helper-module-imports": "^7.8.3", "@babel/helper-plugin-utils": "^7.8.3", "@babel/helper-remap-async-to-generator": "^7.8.3" - }, - "dependencies": { - "@babel/helper-module-imports": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.8.3.tgz", - "integrity": "sha512-R0Bx3jippsbAEtzkpZ/6FIiuzOURPcMjHp+Z6xPe6DtApDJx+w7UYyOLanZqO8+wKR9G10s/FmHXvxaMd9s6Kg==", - "dev": true, - "requires": { - "@babel/types": "^7.8.3" - } - }, - "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", - "dev": true, - "requires": { - "esutils": "^2.0.2", - "lodash": "^4.17.13", - "to-fast-properties": "^2.0.0" - } - } } }, "@babel/plugin-transform-block-scoped-functions": { @@ -1025,9 +1016,9 @@ } }, "@babel/plugin-transform-classes": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.8.6.tgz", - "integrity": "sha512-k9r8qRay/R6v5aWZkrEclEhKO6mc1CCQr2dLsVHBmOQiMpN6I2bpjX3vgnldUWeEI1GHVNByULVxZ4BdP4Hmdg==", + "version": "7.9.2", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.9.2.tgz", + "integrity": "sha512-TC2p3bPzsfvSsqBZo0kJnuelnoK9O3welkUpqSqBQuBF6R5MN2rysopri8kNvtlGIb2jmUO7i15IooAZJjZuMQ==", "dev": true, "requires": { "@babel/helper-annotate-as-pure": "^7.8.3", @@ -1050,9 +1041,9 @@ } }, "@babel/plugin-transform-destructuring": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.8.3.tgz", - "integrity": "sha512-H4X646nCkiEcHZUZaRkhE2XVsoz0J/1x3VVujnn96pSoGCtKPA99ZZA+va+gK+92Zycd6OBKCD8tDb/731bhgQ==", + "version": "7.8.8", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.8.8.tgz", + "integrity": "sha512-eRJu4Vs2rmttFCdhPUM3bV0Yo/xPSdPw6ML9KHs/bjB4bLA5HXlbvYXPOD5yASodGod+krjYx21xm1QmL8dCJQ==", "dev": true, "requires": { "@babel/helper-plugin-utils": "^7.8.3" @@ -1088,9 +1079,9 @@ } }, "@babel/plugin-transform-for-of": { - "version": "7.8.6", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.8.6.tgz", - "integrity": "sha512-M0pw4/1/KI5WAxPsdcUL/w2LJ7o89YHN3yLkzNjg7Yl15GlVGgzHyCU+FMeAxevHGsLVmUqbirlUIKTafPmzdw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.9.0.tgz", + "integrity": "sha512-lTAnWOpMwOXpyDx06N+ywmF3jNbafZEqZ96CGYabxHrxNX8l5ny7dt4bK/rGwAh9utyP2b2Hv7PlZh1AAS54FQ==", "dev": true, "requires": { "@babel/helper-plugin-utils": "^7.8.3" @@ -1125,47 +1116,47 @@ } }, "@babel/plugin-transform-modules-amd": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.8.3.tgz", - "integrity": "sha512-MadJiU3rLKclzT5kBH4yxdry96odTUwuqrZM+GllFI/VhxfPz+k9MshJM+MwhfkCdxxclSbSBbUGciBngR+kEQ==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.9.0.tgz", + "integrity": "sha512-vZgDDF003B14O8zJy0XXLnPH4sg+9X5hFBBGN1V+B2rgrB+J2xIypSN6Rk9imB2hSTHQi5OHLrFWsZab1GMk+Q==", "dev": true, "requires": { - "@babel/helper-module-transforms": "^7.8.3", + "@babel/helper-module-transforms": "^7.9.0", "@babel/helper-plugin-utils": "^7.8.3", "babel-plugin-dynamic-import-node": "^2.3.0" } }, "@babel/plugin-transform-modules-commonjs": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.8.3.tgz", - "integrity": "sha512-JpdMEfA15HZ/1gNuB9XEDlZM1h/gF/YOH7zaZzQu2xCFRfwc01NXBMHHSTT6hRjlXJJs5x/bfODM3LiCk94Sxg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.9.0.tgz", + "integrity": "sha512-qzlCrLnKqio4SlgJ6FMMLBe4bySNis8DFn1VkGmOcxG9gqEyPIOzeQrA//u0HAKrWpJlpZbZMPB1n/OPa4+n8g==", "dev": true, "requires": { - "@babel/helper-module-transforms": "^7.8.3", + "@babel/helper-module-transforms": "^7.9.0", "@babel/helper-plugin-utils": "^7.8.3", "@babel/helper-simple-access": "^7.8.3", "babel-plugin-dynamic-import-node": "^2.3.0" } }, "@babel/plugin-transform-modules-systemjs": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.8.3.tgz", - "integrity": "sha512-8cESMCJjmArMYqa9AO5YuMEkE4ds28tMpZcGZB/jl3n0ZzlsxOAi3mC+SKypTfT8gjMupCnd3YiXCkMjj2jfOg==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.9.0.tgz", + "integrity": "sha512-FsiAv/nao/ud2ZWy4wFacoLOm5uxl0ExSQ7ErvP7jpoihLR6Cq90ilOFyX9UXct3rbtKsAiZ9kFt5XGfPe/5SQ==", "dev": true, "requires": { "@babel/helper-hoist-variables": "^7.8.3", - "@babel/helper-module-transforms": "^7.8.3", + "@babel/helper-module-transforms": "^7.9.0", "@babel/helper-plugin-utils": "^7.8.3", "babel-plugin-dynamic-import-node": "^2.3.0" } }, "@babel/plugin-transform-modules-umd": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.8.3.tgz", - "integrity": "sha512-evhTyWhbwbI3/U6dZAnx/ePoV7H6OUG+OjiJFHmhr9FPn0VShjwC2kdxqIuQ/+1P50TMrneGzMeyMTFOjKSnAw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.9.0.tgz", + "integrity": "sha512-uTWkXkIVtg/JGRSIABdBoMsoIeoHQHPTL0Y2E7xf5Oj7sLqwVsNXOkNk0VJc7vF0IMBsPeikHxFjGe+qmwPtTQ==", "dev": true, "requires": { - "@babel/helper-module-transforms": "^7.8.3", + "@babel/helper-module-transforms": "^7.9.0", "@babel/helper-plugin-utils": "^7.8.3" } }, @@ -1198,12 +1189,11 @@ } }, "@babel/plugin-transform-parameters": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.8.7.tgz", - "integrity": "sha512-brYWaEPTRimOctz2NDA3jnBbDi7SVN2T4wYuu0aqSzxC3nozFZngGaw29CJ9ZPweB7k+iFmZuoG3IVPIcXmD2g==", + "version": "7.9.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.9.3.tgz", + "integrity": "sha512-fzrQFQhp7mIhOzmOtPiKffvCYQSK10NR8t6BBz2yPbeUHb9OLW8RZGtgDRBn8z2hGcwvKDL3vC7ojPTLNxmqEg==", "dev": true, "requires": { - "@babel/helper-call-delegate": "^7.8.7", "@babel/helper-get-function-arity": "^7.8.3", "@babel/helper-plugin-utils": "^7.8.3" } @@ -1293,12 +1283,12 @@ } }, "@babel/preset-env": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.8.7.tgz", - "integrity": "sha512-BYftCVOdAYJk5ASsznKAUl53EMhfBbr8CJ1X+AJLfGPscQkwJFiaV/Wn9DPH/7fzm2v6iRYJKYHSqyynTGw0nw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.9.0.tgz", + "integrity": "sha512-712DeRXT6dyKAM/FMbQTV/FvRCms2hPCx+3weRjZ8iQVQWZejWWk1wwG6ViWMyqb/ouBbGOl5b6aCk0+j1NmsQ==", "dev": true, "requires": { - "@babel/compat-data": "^7.8.6", + "@babel/compat-data": "^7.9.0", "@babel/helper-compilation-targets": "^7.8.7", "@babel/helper-module-imports": "^7.8.3", "@babel/helper-plugin-utils": "^7.8.3", @@ -1306,14 +1296,16 @@ "@babel/plugin-proposal-dynamic-import": "^7.8.3", "@babel/plugin-proposal-json-strings": "^7.8.3", "@babel/plugin-proposal-nullish-coalescing-operator": "^7.8.3", - "@babel/plugin-proposal-object-rest-spread": "^7.8.3", + "@babel/plugin-proposal-numeric-separator": "^7.8.3", + "@babel/plugin-proposal-object-rest-spread": "^7.9.0", "@babel/plugin-proposal-optional-catch-binding": "^7.8.3", - "@babel/plugin-proposal-optional-chaining": "^7.8.3", + "@babel/plugin-proposal-optional-chaining": "^7.9.0", "@babel/plugin-proposal-unicode-property-regex": "^7.8.3", "@babel/plugin-syntax-async-generators": "^7.8.0", "@babel/plugin-syntax-dynamic-import": "^7.8.0", "@babel/plugin-syntax-json-strings": "^7.8.0", "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.0", + "@babel/plugin-syntax-numeric-separator": "^7.8.0", "@babel/plugin-syntax-object-rest-spread": "^7.8.0", "@babel/plugin-syntax-optional-catch-binding": "^7.8.0", "@babel/plugin-syntax-optional-chaining": "^7.8.0", @@ -1322,20 +1314,20 @@ "@babel/plugin-transform-async-to-generator": "^7.8.3", "@babel/plugin-transform-block-scoped-functions": "^7.8.3", "@babel/plugin-transform-block-scoping": "^7.8.3", - "@babel/plugin-transform-classes": "^7.8.6", + "@babel/plugin-transform-classes": "^7.9.0", "@babel/plugin-transform-computed-properties": "^7.8.3", "@babel/plugin-transform-destructuring": "^7.8.3", "@babel/plugin-transform-dotall-regex": "^7.8.3", "@babel/plugin-transform-duplicate-keys": "^7.8.3", "@babel/plugin-transform-exponentiation-operator": "^7.8.3", - "@babel/plugin-transform-for-of": "^7.8.6", + "@babel/plugin-transform-for-of": "^7.9.0", "@babel/plugin-transform-function-name": "^7.8.3", "@babel/plugin-transform-literals": "^7.8.3", "@babel/plugin-transform-member-expression-literals": "^7.8.3", - "@babel/plugin-transform-modules-amd": "^7.8.3", - "@babel/plugin-transform-modules-commonjs": "^7.8.3", - "@babel/plugin-transform-modules-systemjs": "^7.8.3", - "@babel/plugin-transform-modules-umd": "^7.8.3", + "@babel/plugin-transform-modules-amd": "^7.9.0", + "@babel/plugin-transform-modules-commonjs": "^7.9.0", + "@babel/plugin-transform-modules-systemjs": "^7.9.0", + "@babel/plugin-transform-modules-umd": "^7.9.0", "@babel/plugin-transform-named-capturing-groups-regex": "^7.8.3", "@babel/plugin-transform-new-target": "^7.8.3", "@babel/plugin-transform-object-super": "^7.8.3", @@ -1349,49 +1341,54 @@ "@babel/plugin-transform-template-literals": "^7.8.3", "@babel/plugin-transform-typeof-symbol": "^7.8.4", "@babel/plugin-transform-unicode-regex": "^7.8.3", - "@babel/types": "^7.8.7", - "browserslist": "^4.8.5", + "@babel/preset-modules": "^0.1.3", + "@babel/types": "^7.9.0", + "browserslist": "^4.9.1", "core-js-compat": "^3.6.2", "invariant": "^2.2.2", "levenary": "^1.1.1", "semver": "^5.5.0" }, "dependencies": { - "@babel/helper-module-imports": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.8.3.tgz", - "integrity": "sha512-R0Bx3jippsbAEtzkpZ/6FIiuzOURPcMjHp+Z6xPe6DtApDJx+w7UYyOLanZqO8+wKR9G10s/FmHXvxaMd9s6Kg==", - "dev": true, - "requires": { - "@babel/types": "^7.8.3" - } - }, "@babel/types": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.8.7.tgz", - "integrity": "sha512-k2TreEHxFA4CjGkL+GYjRyx35W0Mr7DP5+9q6WMkyKXB+904bYmG40syjMFV0oLlhhFCwWl0vA0DyzTDkwAiJw==", + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.9.0.tgz", + "integrity": "sha512-BS9JKfXkzzJl8RluW4JGknzpiUV7ZrvTayM6yfqLTVBEnFtyowVIOu6rqxRd5cVO6yGoWf4T8u8dgK9oB+GCng==", "dev": true, "requires": { - "esutils": "^2.0.2", + "@babel/helper-validator-identifier": "^7.9.0", "lodash": "^4.17.13", "to-fast-properties": "^2.0.0" } } } }, + "@babel/preset-modules": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.3.tgz", + "integrity": "sha512-Ra3JXOHBq2xd56xSF7lMKXdjBn3T772Y1Wet3yWnkDly9zHvJki029tAFzvAAK5cf4YV3yoxuP61crYRol6SVg==", + "dev": true, + "requires": { + "@babel/helper-plugin-utils": "^7.0.0", + "@babel/plugin-proposal-unicode-property-regex": "^7.4.4", + "@babel/plugin-transform-dotall-regex": "^7.4.4", + "@babel/types": "^7.4.4", + "esutils": "^2.0.2" + } + }, "@babel/runtime": { - "version": "7.8.7", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.8.7.tgz", - "integrity": "sha512-+AATMUFppJDw6aiR5NVPHqIQBlV/Pj8wY/EZH+lmvRdUo9xBaz/rF3alAwFJQavvKfeOlPE7oaaDHVbcySbCsg==", + "version": "7.9.2", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.9.2.tgz", + "integrity": "sha512-NE2DtOdufG7R5vnfQUTehdTfNycfUANEtCa9PssN9O/xmTzP4E08UI797ixaei6hBEVL9BI/PsdJS5x7mWoB9Q==", "dev": true, "requires": { "regenerator-runtime": "^0.13.4" }, "dependencies": { "regenerator-runtime": { - "version": "0.13.4", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.4.tgz", - "integrity": "sha512-plpwicqEzfEyTQohIKktWigcLzmNStMGwbOUbykx51/29Z3JOGYldaaNGK7ngNXV+UcoqvIMmloZ48Sr74sd+g==", + "version": "0.13.5", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.5.tgz", + "integrity": "sha512-ZS5w8CpKFinUzOwW3c83oPeVXoNsrLsaCoLtJvAClH135j/R77RuymhiSErhm2lKcwSCIpmvIWSbDkIfAqKQlA==", "dev": true } } @@ -2778,14 +2775,15 @@ } }, "browserslist": { - "version": "4.9.1", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.9.1.tgz", - "integrity": "sha512-Q0DnKq20End3raFulq6Vfp1ecB9fh8yUNV55s8sekaDDeqBaCtWlRHCUdaWyUeSSBJM7IbM6HcsyaeYqgeDhnw==", + "version": "4.11.0", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.11.0.tgz", + "integrity": "sha512-WqEC7Yr5wUH5sg6ruR++v2SGOQYpyUdYYd4tZoAq1F7y+QXoLoYGXVbxhtaIqWmAJjtNTRjVD3HuJc1OXTel2A==", "dev": true, "requires": { - "caniuse-lite": "^1.0.30001030", - "electron-to-chromium": "^1.3.363", - "node-releases": "^1.1.50" + "caniuse-lite": "^1.0.30001035", + "electron-to-chromium": "^1.3.380", + "node-releases": "^1.1.52", + "pkg-up": "^3.1.0" } }, "buble": { @@ -2960,9 +2958,9 @@ "dev": true }, "caniuse-lite": { - "version": "1.0.30001033", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001033.tgz", - "integrity": "sha512-8Ibzxee6ibc5q88cM1usPsMpJOG5CTq0s/dKOmlekPbDGKt+UrnOOTPSjQz3kVo6yL7N4SB5xd+FGLHQmbzh6A==", + "version": "1.0.30001036", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001036.tgz", + "integrity": "sha512-jU8CIFIj2oR7r4W+5AKcsvWNVIb6Q6OZE3UsrXrZBHFtreT4YgTeOJtTucp+zSedEpTi3L5wASSP0LYIE3if6w==", "dev": true }, "caseless": { @@ -3927,9 +3925,9 @@ "dev": true }, "electron-to-chromium": { - "version": "1.3.372", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.372.tgz", - "integrity": "sha512-77a4jYC52OdisHM+Tne7dgWEvQT1FoNu/jYl279pP88ZtG4ZRIPyhQwAKxj6C2rzsyC1OwsOds9JlZtNncSz6g==", + "version": "1.3.380", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.380.tgz", + "integrity": "sha512-2jhQxJKcjcSpVOQm0NAfuLq8o+130blrcawoumdXT6411xG/xIAOyZodO/y7WTaYlz/NHe3sCCAe/cJLnDsqTw==", "dev": true }, "elliptic": { @@ -8528,9 +8526,9 @@ } }, "node-releases": { - "version": "1.1.51", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.51.tgz", - "integrity": "sha512-1eQEs6HFYY1kMXQPOLzCf7HdjReErmvn85tZESMczdCNVWP3Y7URYLBAyYynuI7yef1zj4HN5q+oB2x67QU0lw==", + "version": "1.1.52", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.52.tgz", + "integrity": "sha512-snSiT1UypkgGt2wxPqS6ImEUICbNCMb31yaxWrOLXjhlt2z2/IBpaOxzONExqSm4y5oLnAqjjRWu+wsDzK5yNQ==", "dev": true, "requires": { "semver": "^6.3.0" @@ -9221,6 +9219,15 @@ "find-up": "^3.0.0" } }, + "pkg-up": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/pkg-up/-/pkg-up-3.1.0.tgz", + "integrity": "sha512-nDywThFk1i4BQK4twPQ6TA4RT8bDY96yeuCVBWL3ePARCiEKDRSrNGbFIgUJpLp+XeIR65v8ra7WuJOFUBtkMA==", + "dev": true, + "requires": { + "find-up": "^3.0.0" + } + }, "pngjs": { "version": "3.4.0", "resolved": "https://registry.npmjs.org/pngjs/-/pngjs-3.4.0.tgz", @@ -9666,9 +9673,9 @@ "dev": true }, "regenerator-transform": { - "version": "0.14.2", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.14.2.tgz", - "integrity": "sha512-V4+lGplCM/ikqi5/mkkpJ06e9Bujq1NFmNLvsCs56zg3ZbzrnUzAtizZ24TXxtRX/W2jcdScwQCnbL0CICTFkQ==", + "version": "0.14.4", + "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.14.4.tgz", + "integrity": "sha512-EaJaKPBI9GvKpvUz2mz4fhx7WPgvwRLY9v3hlNHWmAuJHI13T4nwKnNvm5RWJzEdnI5g5UwtOww+S8IdoUC2bw==", "dev": true, "requires": { "@babel/runtime": "^7.8.4", From d61da37191943646cca4adccce82f09713972e9d Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 09:01:54 +0000 Subject: [PATCH 032/119] Bump coveralls from 3.0.9 to 3.0.11 Bumps [coveralls](https://github.com/nickmerwin/node-coveralls) from 3.0.9 to 3.0.11. - [Release notes](https://github.com/nickmerwin/node-coveralls/releases) - [Commits](https://github.com/nickmerwin/node-coveralls/compare/3.0.9...3.0.11) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 56 +++++++++++++++++++++++------------------------ package.json | 2 +- 2 files changed, 29 insertions(+), 29 deletions(-) diff --git a/package-lock.json b/package-lock.json index 8a619591c5..9a7ed792d7 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2248,9 +2248,9 @@ "dev": true }, "aws4": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.9.0.tgz", - "integrity": "sha512-Uvq6hVe90D0B2WEnUqtdgY1bATGz3mw33nH9Y+dmA+w5DHvUmBgkr5rM/KCHpCsiFNRUfokW/szpPPgMK2hm4A==", + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.9.1.tgz", + "integrity": "sha512-wMHVg2EOHaMRxbzgFJ9gtjOOCrI80OHLG14rxi28XwOW8ux6IiEbRCGGGqCtdAIg4FQCbW20k9RsT4y3gJlFug==", "dev": true }, "babel-code-frame": { @@ -3503,16 +3503,24 @@ "dev": true }, "coveralls": { - "version": "3.0.9", - "resolved": "https://registry.npmjs.org/coveralls/-/coveralls-3.0.9.tgz", - "integrity": "sha512-nNBg3B1+4iDox5A5zqHKzUTiwl2ey4k2o0NEcVZYvl+GOSJdKBj4AJGKLv6h3SvWch7tABHePAQOSZWM9E2hMg==", + "version": "3.0.11", + "resolved": "https://registry.npmjs.org/coveralls/-/coveralls-3.0.11.tgz", + "integrity": "sha512-LZPWPR2NyGKyaABnc49dR0fpeP6UqhvGq4B5nUrTQ1UBy55z96+ga7r+/ChMdMJUwBgyJDXBi88UBgz2rs9IiQ==", "dev": true, "requires": { "js-yaml": "^3.13.1", "lcov-parse": "^1.0.0", "log-driver": "^1.2.7", - "minimist": "^1.2.0", + "minimist": "^1.2.5", "request": "^2.88.0" + }, + "dependencies": { + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + } } }, "create-ecdh": { @@ -9344,9 +9352,9 @@ "dev": true }, "psl": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/psl/-/psl-1.5.0.tgz", - "integrity": "sha512-4vqUjKi2huMu1OJiLhi3jN6jeeKvMZdI1tYgi/njW5zV52jNLgSAZSdN16m9bJFe61/cT8ulmw4qFitV9QRsEA==", + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.7.0.tgz", + "integrity": "sha512-5NsSEDv8zY70ScRnOTn7bK7eanl2MvFrOrS/R6x+dBt5g1ghnj9Zv90kO8GwT8gxcu2ANyFprnFYB85IogIJOQ==", "dev": true }, "public-encrypt": { @@ -9757,9 +9765,9 @@ } }, "request": { - "version": "2.88.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", - "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", + "version": "2.88.2", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.2.tgz", + "integrity": "sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==", "dev": true, "requires": { "aws-sign2": "~0.7.0", @@ -9769,7 +9777,7 @@ "extend": "~3.0.2", "forever-agent": "~0.6.1", "form-data": "~2.3.2", - "har-validator": "~5.1.0", + "har-validator": "~5.1.3", "http-signature": "~1.2.0", "is-typedarray": "~1.0.0", "isstream": "~0.1.2", @@ -9779,7 +9787,7 @@ "performance-now": "^2.1.0", "qs": "~6.5.2", "safe-buffer": "^5.1.2", - "tough-cookie": "~2.4.3", + "tough-cookie": "~2.5.0", "tunnel-agent": "^0.6.0", "uuid": "^3.3.2" } @@ -11616,21 +11624,13 @@ "dev": true }, "tough-cookie": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", - "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz", + "integrity": "sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==", "dev": true, "requires": { - "psl": "^1.1.24", - "punycode": "^1.4.1" - }, - "dependencies": { - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", - "dev": true - } + "psl": "^1.1.28", + "punycode": "^2.1.1" } }, "trim-right": { diff --git a/package.json b/package.json index 71d43f81cb..4c1f38752a 100644 --- a/package.json +++ b/package.json @@ -59,7 +59,7 @@ "chaikin-smooth": "^1.0.4", "clean-css-cli": "4.3.0", "copy-webpack-plugin": "^5.0.4", - "coveralls": "3.0.9", + "coveralls": "3.0.11", "eslint": "^6.0.0", "eslint-config-openlayers": "^13.0.0", "expect.js": "0.3.1", From 2b6e767840292db180d7312aae23db68497e021c Mon Sep 17 00:00:00 2001 From: Jiri Lysek Date: Mon, 23 Mar 2020 10:10:12 +0100 Subject: [PATCH 033/119] encoding color into KML --- src/ol/format/KML.js | 8 +++++++- test/spec/ol/format/kml.test.js | 4 +++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/src/ol/format/KML.js b/src/ol/format/KML.js index 2833548651..88b69bbc98 100644 --- a/src/ol/format/KML.js +++ b/src/ol/format/KML.js @@ -2452,7 +2452,7 @@ function writeIcon(node, icon, objectStack) { // @ts-ignore const ICON_STYLE_SEQUENCE = makeStructureNS( NAMESPACE_URIS, [ - 'scale', 'heading', 'Icon', 'hotSpot' + 'scale', 'heading', 'Icon', 'color', 'hotSpot' ]); @@ -2464,6 +2464,7 @@ const ICON_STYLE_SEQUENCE = makeStructureNS( const ICON_STYLE_SERIALIZERS = makeStructureNS( NAMESPACE_URIS, { 'Icon': makeChildAppender(writeIcon), + 'color': makeChildAppender(writeColorTextNode), 'heading': makeChildAppender(writeDecimalTextNode), 'hotSpot': makeChildAppender(writeVec2), 'scale': makeChildAppender(writeScaleTextNode) @@ -2519,6 +2520,11 @@ function writeIconStyle(node, style, objectStack) { properties['heading'] = rotation; // 0-360 } + const color = style.getColor(); + if (color) { + properties['color'] = color; + } + const parentNode = objectStack[objectStack.length - 1].node; const orderedKeys = ICON_STYLE_SEQUENCE[parentNode.namespaceURI]; const values = makeSequence(properties, orderedKeys); diff --git a/test/spec/ol/format/kml.test.js b/test/spec/ol/format/kml.test.js index 7adedfc2c8..7369705db5 100644 --- a/test/spec/ol/format/kml.test.js +++ b/test/spec/ol/format/kml.test.js @@ -2394,7 +2394,8 @@ describe('ol.format.KML', function() { rotation: 45, scale: 0.5, size: [48, 48], - src: 'http://foo.png' + src: 'http://foo.png', + color: 'rgba(255,0,0,1)' }) }); const imageStyle = style.getImage(); @@ -2420,6 +2421,7 @@ describe('ol.format.KML', function() { ' 48' + ' 48' + ' ' + + ' ff0000ff' + ' ' + ' ' + From 3512638900d40017d2fd1a90e216bf62ca4ef84a Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 09:18:35 +0000 Subject: [PATCH 034/119] Bump mocha from 7.1.0 to 7.1.1 Bumps [mocha](https://github.com/mochajs/mocha) from 7.1.0 to 7.1.1. - [Release notes](https://github.com/mochajs/mocha/releases) - [Changelog](https://github.com/mochajs/mocha/blob/master/CHANGELOG.md) - [Commits](https://github.com/mochajs/mocha/compare/v7.1.0...v7.1.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 75 ++++++++++++++++++++++++++++++++++------------- package.json | 2 +- 2 files changed, 56 insertions(+), 21 deletions(-) diff --git a/package-lock.json b/package-lock.json index 0f5b5d5726..fad3bf0637 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8131,9 +8131,9 @@ } }, "mocha": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-7.1.0.tgz", - "integrity": "sha512-MymHK8UkU0K15Q/zX7uflZgVoRWiTjy0fXE/QjKts6mowUvGxOdPhZ2qj3b0iZdUrNZlW9LAIMFHB4IW+2b3EQ==", + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/mocha/-/mocha-7.1.1.tgz", + "integrity": "sha512-3qQsu3ijNS3GkWcccT5Zw0hf/rWvu1fTN9sPvEd81hlwsr30GX2GcDSSoBxo24IR8FelmrAydGC6/1J5QQP4WA==", "dev": true, "requires": { "ansi-colors": "3.2.3", @@ -8149,7 +8149,7 @@ "js-yaml": "3.13.1", "log-symbols": "3.0.0", "minimatch": "3.0.4", - "mkdirp": "0.5.1", + "mkdirp": "0.5.3", "ms": "2.1.1", "node-environment-flags": "1.0.6", "object.assign": "4.1.0", @@ -8157,8 +8157,8 @@ "supports-color": "6.0.0", "which": "1.3.1", "wide-align": "1.1.3", - "yargs": "13.3.0", - "yargs-parser": "13.1.1", + "yargs": "13.3.2", + "yargs-parser": "13.1.2", "yargs-unparser": "1.6.0" }, "dependencies": { @@ -8266,9 +8266,9 @@ } }, "glob-parent": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.0.tgz", - "integrity": "sha512-qjtRgnIVmOfnKUE3NJAQEdk+lKrxfw8t5ke7SXtfMTHcjsBfOfWXCQfdb30zfDoZQ2IRSIiidmjtbHZPZ++Ihw==", + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.1.tgz", + "integrity": "sha512-FnI+VGOpnlGHWZxthPGR+QhR78fuiK0sNLkHQv+bL9fQi57lNNdquIbna/WrfROrolq8GK5Ek6BiMwqL/voRYQ==", "dev": true, "requires": { "is-glob": "^4.0.1" @@ -8289,6 +8289,21 @@ "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", "dev": true }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "mkdirp": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.3.tgz", + "integrity": "sha512-P+2gwrFqx8lhew375MQHHeTlY8AuOJSrGf0R5ddkEndUkmwpgUob/vQuBD1V22/Cw1/lJr4x+EjllSezBThzBg==", + "dev": true, + "requires": { + "minimist": "^1.2.5" + } + }, "readdirp": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.2.0.tgz", @@ -8348,9 +8363,9 @@ } }, "yargs": { - "version": "13.3.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-13.3.0.tgz", - "integrity": "sha512-2eehun/8ALW8TLoIl7MVaRUrg+yCnenu8B4kBlRxj3GJGDKU1Og7sMXPNm1BYyM1DOJmTZ4YeN/Nwxv+8XJsUA==", + "version": "13.3.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-13.3.2.tgz", + "integrity": "sha512-AX3Zw5iPruN5ie6xGRIDgqkT+ZhnRlZMLMHAs8tg7nRruy2Nb+i5o9bwghAogtM08q1dpr2LVoS8KSTMYpWXUw==", "dev": true, "requires": { "cliui": "^5.0.0", @@ -8362,7 +8377,17 @@ "string-width": "^3.0.0", "which-module": "^2.0.0", "y18n": "^4.0.0", - "yargs-parser": "^13.1.1" + "yargs-parser": "^13.1.2" + } + }, + "yargs-parser": { + "version": "13.1.2", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-13.1.2.tgz", + "integrity": "sha512-3lbsNRf/j+A4QuSZfDRA7HRSfWrzO0YjqTJd5kjAq37Zep1CEgaYmrH9Q3GwPiB9cHyd1Y1UwggGhJGoxipbzg==", + "dev": true, + "requires": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" } } } @@ -8685,9 +8710,9 @@ }, "dependencies": { "es-abstract": { - "version": "1.17.4", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.17.4.tgz", - "integrity": "sha512-Ae3um/gb8F0mui/jPL+QiqmglkUsaQf7FwBEHYIFkztkneosu9imhqHpBzQ3h1vit8t5iQ74t6PEVvphBZiuiQ==", + "version": "1.17.5", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.17.5.tgz", + "integrity": "sha512-BR9auzDbySxOcfog0tLECW8l28eRGpDpU3Dm3Hp4q/N+VtLTmyj4EUN088XZWQDW/hzj6sYRDXeOFsaAODKvpg==", "dev": true, "requires": { "es-to-primitive": "^1.2.1", @@ -12812,9 +12837,9 @@ } }, "yargs": { - "version": "13.3.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-13.3.0.tgz", - "integrity": "sha512-2eehun/8ALW8TLoIl7MVaRUrg+yCnenu8B4kBlRxj3GJGDKU1Og7sMXPNm1BYyM1DOJmTZ4YeN/Nwxv+8XJsUA==", + "version": "13.3.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-13.3.2.tgz", + "integrity": "sha512-AX3Zw5iPruN5ie6xGRIDgqkT+ZhnRlZMLMHAs8tg7nRruy2Nb+i5o9bwghAogtM08q1dpr2LVoS8KSTMYpWXUw==", "dev": true, "requires": { "cliui": "^5.0.0", @@ -12826,7 +12851,17 @@ "string-width": "^3.0.0", "which-module": "^2.0.0", "y18n": "^4.0.0", - "yargs-parser": "^13.1.1" + "yargs-parser": "^13.1.2" + } + }, + "yargs-parser": { + "version": "13.1.2", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-13.1.2.tgz", + "integrity": "sha512-3lbsNRf/j+A4QuSZfDRA7HRSfWrzO0YjqTJd5kjAq37Zep1CEgaYmrH9Q3GwPiB9cHyd1Y1UwggGhJGoxipbzg==", + "dev": true, + "requires": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" } } } diff --git a/package.json b/package.json index 60257ed2fe..ddf4f3d125 100644 --- a/package.json +++ b/package.json @@ -82,7 +82,7 @@ "karma-webpack": "^4.0.0-rc.2", "loglevelnext": "^3.0.1", "marked": "0.8.2", - "mocha": "7.1.0", + "mocha": "7.1.1", "ol-mapbox-style": "^6.0.0", "pixelmatch": "^5.1.0", "pngjs": "^3.4.0", From b70c9a70f86a5b6f98a9ef19ed858f75a9bf23a2 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 23 Mar 2020 09:44:03 +0000 Subject: [PATCH 035/119] Bump ol-mapbox-style from 6.0.1 to 6.1.0 Bumps [ol-mapbox-style](https://github.com/openlayers/ol-mapbox-style) from 6.0.1 to 6.1.0. - [Release notes](https://github.com/openlayers/ol-mapbox-style/releases) - [Changelog](https://github.com/openlayers/ol-mapbox-style/blob/master/CHANGELOG.md) - [Commits](https://github.com/openlayers/ol-mapbox-style/compare/v6.0.1...v6.1.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/package-lock.json b/package-lock.json index fad3bf0637..bad0b6d828 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1520,9 +1520,9 @@ "dev": true }, "@mapbox/mapbox-gl-style-spec": { - "version": "13.11.0", - "resolved": "https://registry.npmjs.org/@mapbox/mapbox-gl-style-spec/-/mapbox-gl-style-spec-13.11.0.tgz", - "integrity": "sha512-OIMGgdp7+KLvSC0v699sXIo7AmBko7XRhsMLCWkxkFfVo7qyUxVkoDpU+xpfvghPteLYy4d30C9sVSQH8IKFwA==", + "version": "13.12.0", + "resolved": "https://registry.npmjs.org/@mapbox/mapbox-gl-style-spec/-/mapbox-gl-style-spec-13.12.0.tgz", + "integrity": "sha512-tRSvlYUI73LOkvS1iQhVwnltoI/QC4ZaLOAS6NM6zx0NwJfsGUJDPucsaKif8l7Sce1ECLd8LYs1MRCyJjdo5Q==", "dev": true, "requires": { "@mapbox/jsonlint-lines-primitives": "~2.0.2", @@ -8816,9 +8816,9 @@ "dev": true }, "ol-mapbox-style": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/ol-mapbox-style/-/ol-mapbox-style-6.0.1.tgz", - "integrity": "sha512-+yIQk4gnb+nMPBuP+8H+orsXQi2okiTvOmnS1IPFBMCAyQurKsfUVuwCmvXS1FYewkD3EryOxtUOug7AFArZkg==", + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/ol-mapbox-style/-/ol-mapbox-style-6.1.0.tgz", + "integrity": "sha512-52nrvbYi8+Zkn4+4EZ92ZJMCLW50RKCgtPm7LNXyZJkz/PCtRZJ440Jy4hPWMON7swV2O9Xjyg+HD8Xv00VFgw==", "dev": true, "requires": { "@mapbox/mapbox-gl-style-spec": "^13.11.0", From 3944a5a0387e4a686aac2033c13153d8cc340c33 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 4 Mar 2020 15:59:52 +0100 Subject: [PATCH 036/119] Make DEVICE_PIXEL_RATIO work in non-window context --- src/ol/has.js | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/ol/has.js b/src/ol/has.js index bfc8aabef3..9bf3e354bf 100644 --- a/src/ol/has.js +++ b/src/ol/has.js @@ -37,7 +37,13 @@ export const MAC = ua.indexOf('macintosh') !== -1; * @type {number} * @api */ -export const DEVICE_PIXEL_RATIO = window.devicePixelRatio || 1; +export const DEVICE_PIXEL_RATIO = (function() { + try { + return self.devicePixelRatio; + } catch (e) { + return window.devicePixelRatio || 1; + } +})(); /** * Image.prototype.decode() is supported. From f896d9fb03d06a7743a194ad55897026002f934e Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 4 Mar 2020 16:01:43 +0100 Subject: [PATCH 037/119] Move tile priority function to the TileQueue module --- src/ol/PluggableMap.js | 24 ++---------------------- src/ol/TileQueue.js | 33 ++++++++++++++++++++++++++++++++- 2 files changed, 34 insertions(+), 23 deletions(-) diff --git a/src/ol/PluggableMap.js b/src/ol/PluggableMap.js index eb6c7646e4..792215e1cc 100644 --- a/src/ol/PluggableMap.js +++ b/src/ol/PluggableMap.js @@ -12,7 +12,7 @@ import MapProperty from './MapProperty.js'; import RenderEventType from './render/EventType.js'; import BaseObject, {getChangeEventType} from './Object.js'; import ObjectEventType from './ObjectEventType.js'; -import TileQueue from './TileQueue.js'; +import TileQueue, {getTilePriority} from './TileQueue.js'; import View from './View.js'; import ViewHint from './ViewHint.js'; import {assert} from './asserts.js'; @@ -24,7 +24,6 @@ import {TRUE} from './functions.js'; import {DEVICE_PIXEL_RATIO, IMAGE_DECODE, PASSIVE_EVENT_LISTENERS} from './has.js'; import LayerGroup from './layer/Group.js'; import {hasArea} from './size.js'; -import {DROP} from './structs/PriorityQueue.js'; import {create as createTransform, apply as applyTransform} from './transform.js'; import {toUserCoordinate, fromUserCoordinate} from './proj.js'; @@ -891,26 +890,7 @@ class PluggableMap extends BaseObject { * @return {number} Tile priority. */ getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { - // Filter out tiles at higher zoom levels than the current zoom level, or that - // are outside the visible extent. - const frameState = this.frameState_; - if (!frameState || !(tileSourceKey in frameState.wantedTiles)) { - return DROP; - } - if (!frameState.wantedTiles[tileSourceKey][tile.getKey()]) { - return DROP; - } - // Prioritize the highest zoom level tiles closest to the focus. - // Tiles at higher zoom levels are prioritized using Math.log(tileResolution). - // Within a zoom level, tiles are prioritized by the distance in pixels between - // the center of the tile and the center of the viewport. The factor of 65536 - // means that the prioritization should behave as desired for tiles up to - // 65536 * Math.log(2) = 45426 pixels from the focus. - const center = frameState.viewState.center; - const deltaX = tileCenter[0] - center[0]; - const deltaY = tileCenter[1] - center[1]; - return 65536 * Math.log(tileResolution) + - Math.sqrt(deltaX * deltaX + deltaY * deltaY) / tileResolution; + return getTilePriority(this.frameState_, tile, tileSourceKey, tileCenter, tileResolution); } /** diff --git a/src/ol/TileQueue.js b/src/ol/TileQueue.js index 994a8eeb1d..eb39b119d8 100644 --- a/src/ol/TileQueue.js +++ b/src/ol/TileQueue.js @@ -3,7 +3,7 @@ */ import TileState from './TileState.js'; import EventType from './events/EventType.js'; -import PriorityQueue from './structs/PriorityQueue.js'; +import PriorityQueue, {DROP} from './structs/PriorityQueue.js'; /** @@ -119,3 +119,34 @@ class TileQueue extends PriorityQueue { export default TileQueue; + + +/** + * @param {import('./PluggableMap.js').FrameState} frameState Frame state. + * @param {import("./Tile.js").default} tile Tile. + * @param {string} tileSourceKey Tile source key. + * @param {import("./coordinate.js").Coordinate} tileCenter Tile center. + * @param {number} tileResolution Tile resolution. + * @return {number} Tile priority. + */ +export function getTilePriority(frameState, tile, tileSourceKey, tileCenter, tileResolution) { + // Filter out tiles at higher zoom levels than the current zoom level, or that + // are outside the visible extent. + if (!frameState || !(tileSourceKey in frameState.wantedTiles)) { + return DROP; + } + if (!frameState.wantedTiles[tileSourceKey][tile.getKey()]) { + return DROP; + } + // Prioritize the highest zoom level tiles closest to the focus. + // Tiles at higher zoom levels are prioritized using Math.log(tileResolution). + // Within a zoom level, tiles are prioritized by the distance in pixels between + // the center of the tile and the center of the viewport. The factor of 65536 + // means that the prioritization should behave as desired for tiles up to + // 65536 * Math.log(2) = 45426 pixels from the focus. + const center = frameState.viewState.center; + const deltaX = tileCenter[0] - center[0]; + const deltaY = tileCenter[1] - center[1]; + return 65536 * Math.log(tileResolution) + + Math.sqrt(deltaX * deltaX + deltaY * deltaY) / tileResolution; +} From 717b8ad0cf90f5505fb238d1f00366725e6ded28 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 4 Mar 2020 16:02:07 +0100 Subject: [PATCH 038/119] Make createCanvasContext2D work in non-window context --- src/ol/dom.js | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/ol/dom.js b/src/ol/dom.js index ad10c14671..37d188541e 100644 --- a/src/ol/dom.js +++ b/src/ol/dom.js @@ -3,6 +3,7 @@ */ +//FIXME Move this function to the canvas module /** * Create an html canvas element and returns its 2d context. * @param {number=} opt_width Canvas width. @@ -12,14 +13,18 @@ */ export function createCanvasContext2D(opt_width, opt_height, opt_canvasPool) { const canvas = opt_canvasPool && opt_canvasPool.length ? - opt_canvasPool.shift() : document.createElement('canvas'); + opt_canvasPool.shift() : + 'document' in self ? + document.createElement('canvas') : + new OffscreenCanvas(opt_width || 300, opt_height || 300); if (opt_width) { canvas.width = opt_width; } if (opt_height) { canvas.height = opt_height; } - return canvas.getContext('2d'); + //FIXME Allow OffscreenCanvasRenderingContext2D as return type + return /** @type {CanvasRenderingContext2D} */ (canvas.getContext('2d')); } From 8b76f52652f9a6bf8fb2433fd6d41d213a65e34f Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 4 Mar 2020 16:03:09 +0100 Subject: [PATCH 039/119] Make createTransformString work in non-window context --- src/ol/renderer/canvas/Layer.js | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/ol/renderer/canvas/Layer.js b/src/ol/renderer/canvas/Layer.js index d082f13923..5be2536e07 100644 --- a/src/ol/renderer/canvas/Layer.js +++ b/src/ol/renderer/canvas/Layer.js @@ -73,7 +73,7 @@ class CanvasLayerRenderer extends LayerRenderer { * @type {HTMLCanvasElement} * @private */ - this.createTransformStringCanvas_ = createCanvasContext2D(1, 1).canvas; + this.createTransformStringCanvas_ = 'document' in self ? createCanvasContext2D(1, 1).canvas : null; } @@ -274,8 +274,12 @@ class CanvasLayerRenderer extends LayerRenderer { * @return {string} CSS transform. */ createTransformString(transform) { - this.createTransformStringCanvas_.style.transform = toString(transform); - return this.createTransformStringCanvas_.style.transform; + if (this.createTransformStringCanvas_) { + this.createTransformStringCanvas_.style.transform = toString(transform); + return this.createTransformStringCanvas_.style.transform; + } else { + return toString(transform); + } } } From 3f5022630b72ed0185d15fa96231285cfd263134 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 4 Mar 2020 16:06:18 +0100 Subject: [PATCH 040/119] Create a basic example for OffscreenCanvas rendering --- examples/mvtlayer.worker.js | 75 ++++++++++++++++++++++++++++ examples/offscreen-canvas-tiles.html | 9 ++++ examples/offscreen-canvas-tiles.js | 63 +++++++++++++++++++++++ package-lock.json | 22 ++++++++ package.json | 1 + 5 files changed, 170 insertions(+) create mode 100644 examples/mvtlayer.worker.js create mode 100644 examples/offscreen-canvas-tiles.html create mode 100644 examples/offscreen-canvas-tiles.js diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js new file mode 100644 index 0000000000..6de3774f1d --- /dev/null +++ b/examples/mvtlayer.worker.js @@ -0,0 +1,75 @@ +import VectorTileLayer from '../src/ol/layer/VectorTile.js'; +import VectorTileSource from '../src/ol/source/VectorTile.js'; +import MVT from '../src/ol/format/MVT.js'; +import {Projection} from '../src/ol/proj.js'; +import TileQueue from '../src/ol/TileQueue.js'; +import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; + +const key = 'pk.eyJ1IjoiYWhvY2V2YXIiLCJhIjoiY2pzbmg0Nmk5MGF5NzQzbzRnbDNoeHJrbiJ9.7_-_gL8ur7ZtEiNwRfCy7Q'; + +/** @type {any} */ +const worker = self; + +let frameState; + +function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { + return tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution); +} + +const layer = new VectorTileLayer({ + declutter: true, + source: new VectorTileSource({ + format: new MVT(), + url: 'https://{a-d}.tiles.mapbox.com/v4/mapbox.mapbox-streets-v6/' + + '{z}/{x}/{y}.vector.pbf?access_token=' + key + }) +}); +const tileQueue = new TileQueue(getTilePriority, function() { + worker.postMessage({type: 'render'}); +}); +const maxTotalLoading = 8; +const maxNewLoads = 2; + +const renderer = layer.getRenderer(); + +renderer.useContainer = function(target, transform, opacity) { + target.style = {}; + this.canvas = target; + this.context = target.getContext('2d'); + this.container = { + firstElementChild: target + }; + worker.postMessage({ + type: 'transform-opacity', + transform: transform, + opacity: opacity + }); +}; + +let canvas; +let rendering = false; + +worker.onmessage = function(event) { + if (rendering) { + // drop this frame + return; + } + if (event.data.canvas) { + canvas = event.data.canvas; + } else { + frameState = event.data.frameState; + frameState.tileQueue = tileQueue; + frameState.viewState.projection.__proto__ = Projection.prototype; + rendering = true; + requestAnimationFrame(function() { + renderer.renderFrame(frameState, canvas); + if (tileQueue.getTilesLoading() < maxTotalLoading) { + tileQueue.reprioritize(); // FIXME only call if view has changed + tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); + } + rendering = false; + }); + } +}; + +export let create; diff --git a/examples/offscreen-canvas-tiles.html b/examples/offscreen-canvas-tiles.html new file mode 100644 index 0000000000..231da2f14f --- /dev/null +++ b/examples/offscreen-canvas-tiles.html @@ -0,0 +1,9 @@ +--- +layout: example.html +title: Vector tiles rendered in an offscreen canvas +shortdesc: Example of a map that delegates rendering to a worker. +docs: > + The map in this example is rendered in a web worker, using `OffscreenCanvas`. **Note:** This is currently only supported in Chrome and Edge. +tags: "worker, offscreencanvas, vector-tiles" +--- +
diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js new file mode 100644 index 0000000000..af9f43e03f --- /dev/null +++ b/examples/offscreen-canvas-tiles.js @@ -0,0 +1,63 @@ +import Map from '../src/ol/Map.js'; +import View from '../src/ol/View.js'; +import Layer from '../src/ol/layer/Layer.js'; +//eslint-disable-next-line +import Worker from 'worker-loader!./mvtlayer.worker.js'; + +const mvtLayerWorker = new Worker(); + +function getCircularReplacer() { + const seen = new WeakSet(); + return function(key, value) { + if (typeof value === 'object' && value !== null) { + if (seen.has(value)) { + return '[circular]'; + } + seen.add(value); + } + return value; + }; +} + +let container, canvas; + +const map = new Map({ + layers: [ + new Layer({ + render: function(frameState) { + if (!container) { + container = document.createElement('div'); + container.style.position = 'absolute'; + container.style.width = '100%'; + container.style.height = '100%'; + canvas = document.createElement('canvas'); + canvas.style.position = 'absolute'; + canvas.style.left = '0'; + canvas.style.transformOrigin = 'top left'; + container.appendChild(canvas); + const offscreen = canvas.transferControlToOffscreen(); + mvtLayerWorker.postMessage({ + canvas: offscreen + }, [offscreen]); + } + mvtLayerWorker.postMessage({ + frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + }); + return container; + } + }) + ], + target: 'map', + view: new View({ + center: [0, 0], + zoom: 2 + }) +}); +mvtLayerWorker.addEventListener('message', message => { + if (message.data.type === 'render') { + map.render(); + } else if (canvas && message.data.type === 'transform-opacity') { + canvas.style.transform = message.data.transform; + canvas.style.opacity = message.data.opacity; + } +}); diff --git a/package-lock.json b/package-lock.json index 9bced339b2..450a9667f9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -12693,6 +12693,28 @@ "errno": "~0.1.7" } }, + "worker-loader": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/worker-loader/-/worker-loader-2.0.0.tgz", + "integrity": "sha512-tnvNp4K3KQOpfRnD20m8xltE3eWh89Ye+5oj7wXEEHKac1P4oZ6p9oTj8/8ExqoSBnk9nu5Pr4nKfQ1hn2APJw==", + "dev": true, + "requires": { + "loader-utils": "^1.0.0", + "schema-utils": "^0.4.0" + }, + "dependencies": { + "schema-utils": { + "version": "0.4.7", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-0.4.7.tgz", + "integrity": "sha512-v/iwU6wvwGK8HbU9yi3/nhGzP0yGSuhQMzL6ySiec1FSrZZDkhm4noOSWzrNFo/jEc+SJY6jRTwuwbSXJPDUnQ==", + "dev": true, + "requires": { + "ajv": "^6.1.0", + "ajv-keywords": "^3.1.0" + } + } + } + }, "wrap-ansi": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", diff --git a/package.json b/package.json index 2fa01fd358..d9adcfa006 100644 --- a/package.json +++ b/package.json @@ -104,6 +104,7 @@ "webpack-cli": "^3.3.2", "webpack-dev-middleware": "^3.6.2", "webpack-dev-server": "^3.3.1", + "worker-loader": "^2.0.0", "yargs": "^15.0.2" }, "eslintConfig": { From 56edbb2d736d1f8aad6b03075d57d939d9f16513 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Thu, 12 Mar 2020 11:46:40 +0100 Subject: [PATCH 041/119] Make createTransformToString a standalone function --- src/ol/has.js | 14 ++++++++++++++ src/ol/render/canvas.js | 24 ++++++++++++++++++++++++ src/ol/renderer/canvas/ImageLayer.js | 3 ++- src/ol/renderer/canvas/Layer.js | 22 ++-------------------- src/ol/renderer/canvas/TileLayer.js | 3 ++- 5 files changed, 44 insertions(+), 22 deletions(-) diff --git a/src/ol/has.js b/src/ol/has.js index 9bf3e354bf..24b053a2fe 100644 --- a/src/ol/has.js +++ b/src/ol/has.js @@ -45,6 +45,20 @@ export const DEVICE_PIXEL_RATIO = (function() { } })(); +/** + * The execution context is a window. + * @const + * @type {boolean} + */ +export const WINDOW = (function() { + try { + return 'document' in self; + } catch (e) { + // ancient browsers don't have `self` + return true; + } +})(); + /** * Image.prototype.decode() is supported. * @type {boolean} diff --git a/src/ol/render/canvas.js b/src/ol/render/canvas.js index adb892dd34..04781b9bc1 100644 --- a/src/ol/render/canvas.js +++ b/src/ol/render/canvas.js @@ -6,6 +6,8 @@ import {createCanvasContext2D} from '../dom.js'; import {clear} from '../obj.js'; import BaseObject from '../Object.js'; import EventTarget from '../events/Target.js'; +import {WINDOW} from '../has.js'; +import {toString} from '../transform.js'; /** @@ -438,3 +440,25 @@ function executeLabelInstructions(label, context) { } } } + +/** + * @type {HTMLCanvasElement} + * @private + */ +let createTransformStringCanvas = null; + +/** + * @param {import("../transform.js").Transform} transform Transform. + * @return {string} CSS transform. + */ +export function createTransformString(transform) { + if (WINDOW) { + if (!createTransformStringCanvas) { + createTransformStringCanvas = createCanvasContext2D(1, 1).canvas; + } + createTransformStringCanvas.style.transform = toString(transform); + return createTransformStringCanvas.style.transform; + } else { + return toString(transform); + } +} diff --git a/src/ol/renderer/canvas/ImageLayer.js b/src/ol/renderer/canvas/ImageLayer.js index 7403890219..bd11ac74b3 100644 --- a/src/ol/renderer/canvas/ImageLayer.js +++ b/src/ol/renderer/canvas/ImageLayer.js @@ -8,6 +8,7 @@ import {fromUserExtent} from '../../proj.js'; import {getIntersection, isEmpty} from '../../extent.js'; import CanvasLayerRenderer from './Layer.js'; import {compose as composeTransform, makeInverse} from '../../transform.js'; +import {createTransformString} from '../../render/canvas.js'; /** * @classdesc @@ -109,7 +110,7 @@ class CanvasImageLayerRenderer extends CanvasLayerRenderer { ); makeInverse(this.inversePixelTransform, this.pixelTransform); - const canvasTransform = this.createTransformString(this.pixelTransform); + const canvasTransform = createTransformString(this.pixelTransform); this.useContainer(target, canvasTransform, layerState.opacity); diff --git a/src/ol/renderer/canvas/Layer.js b/src/ol/renderer/canvas/Layer.js index 5be2536e07..57338822b1 100644 --- a/src/ol/renderer/canvas/Layer.js +++ b/src/ol/renderer/canvas/Layer.js @@ -7,7 +7,7 @@ import RenderEvent from '../../render/Event.js'; import RenderEventType from '../../render/EventType.js'; import {rotateAtOffset} from '../../render/canvas.js'; import LayerRenderer from '../Layer.js'; -import {create as createTransform, apply as applyTransform, compose as composeTransform, toString} from '../../transform.js'; +import {create as createTransform, apply as applyTransform, compose as composeTransform} from '../../transform.js'; /** * @abstract @@ -69,12 +69,6 @@ class CanvasLayerRenderer extends LayerRenderer { */ this.containerReused = false; - /** - * @type {HTMLCanvasElement} - * @private - */ - this.createTransformStringCanvas_ = 'document' in self ? createCanvasContext2D(1, 1).canvas : null; - } /** @@ -269,19 +263,7 @@ class CanvasLayerRenderer extends LayerRenderer { return data; } - /** - * @param {import("../../transform.js").Transform} transform Transform. - * @return {string} CSS transform. - */ - createTransformString(transform) { - if (this.createTransformStringCanvas_) { - this.createTransformStringCanvas_.style.transform = toString(transform); - return this.createTransformStringCanvas_.style.transform; - } else { - return toString(transform); - } - } - } export default CanvasLayerRenderer; + diff --git a/src/ol/renderer/canvas/TileLayer.js b/src/ol/renderer/canvas/TileLayer.js index 51fb12939f..51a4d8a372 100644 --- a/src/ol/renderer/canvas/TileLayer.js +++ b/src/ol/renderer/canvas/TileLayer.js @@ -9,6 +9,7 @@ import {createEmpty, equals, getIntersection, getTopLeft} from '../../extent.js' import CanvasLayerRenderer from './Layer.js'; import {apply as applyTransform, compose as composeTransform, makeInverse} from '../../transform.js'; import {numberSafeCompareFunction} from '../../array.js'; +import {createTransformString} from '../../render/canvas.js'; /** * @classdesc @@ -243,7 +244,7 @@ class CanvasTileLayerRenderer extends CanvasLayerRenderer { -width / 2, -height / 2 ); - const canvasTransform = this.createTransformString(this.pixelTransform); + const canvasTransform = createTransformString(this.pixelTransform); this.useContainer(target, canvasTransform, layerState.opacity); const context = this.context; From a93edb338b85eba13128f122039e6bdf9a173d5d Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Fri, 13 Mar 2020 15:52:46 +0100 Subject: [PATCH 042/119] Instant UI feedback --- examples/mvtlayer.worker.js | 61 +++++++++++++++++++----------- examples/offscreen-canvas-tiles.js | 53 +++++++++++++++++++++----- 2 files changed, 81 insertions(+), 33 deletions(-) diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js index 6de3774f1d..bc2ab5a20b 100644 --- a/examples/mvtlayer.worker.js +++ b/examples/mvtlayer.worker.js @@ -11,6 +11,20 @@ const key = 'pk.eyJ1IjoiYWhvY2V2YXIiLCJhIjoiY2pzbmg0Nmk5MGF5NzQzbzRnbDNoeHJrbiJ9 const worker = self; let frameState; +const canvas = new OffscreenCanvas(1, 1); + +function getCircularReplacer() { + const seen = new WeakSet(); + return function(key, value) { + if (typeof value === 'object' && value !== null) { + if (seen.has(value)) { + return '[circular]'; + } + seen.add(value); + } + return value; + }; +} function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { return tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution); @@ -24,13 +38,13 @@ const layer = new VectorTileLayer({ '{z}/{x}/{y}.vector.pbf?access_token=' + key }) }); +const renderer = layer.getRenderer(); const tileQueue = new TileQueue(getTilePriority, function() { - worker.postMessage({type: 'render'}); + worker.postMessage({type: 'request-render'}); }); const maxTotalLoading = 8; const maxNewLoads = 2; -const renderer = layer.getRenderer(); renderer.useContainer = function(target, transform, opacity) { target.style = {}; @@ -39,37 +53,38 @@ renderer.useContainer = function(target, transform, opacity) { this.container = { firstElementChild: target }; - worker.postMessage({ - type: 'transform-opacity', - transform: transform, - opacity: opacity + layer.once('postrender', function() { + const imageData = canvas.transferToImageBitmap(); + worker.postMessage({ + type: 'rendered', + imageData: imageData, + transform: transform, + opacity: opacity, + frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + }, [imageData]); }); }; -let canvas; let rendering = false; worker.onmessage = function(event) { if (rendering) { // drop this frame + worker.postMessage({type: 'request-render'}); return; } - if (event.data.canvas) { - canvas = event.data.canvas; - } else { - frameState = event.data.frameState; - frameState.tileQueue = tileQueue; - frameState.viewState.projection.__proto__ = Projection.prototype; - rendering = true; - requestAnimationFrame(function() { - renderer.renderFrame(frameState, canvas); - if (tileQueue.getTilesLoading() < maxTotalLoading) { - tileQueue.reprioritize(); // FIXME only call if view has changed - tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); - } - rendering = false; - }); - } + frameState = event.data.frameState; + frameState.tileQueue = tileQueue; + frameState.viewState.projection.__proto__ = Projection.prototype; + rendering = true; + requestAnimationFrame(function() { + renderer.renderFrame(frameState, canvas); + if (tileQueue.getTilesLoading() < maxTotalLoading) { + tileQueue.reprioritize(); // FIXME only call if view has changed + tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); + } + rendering = false; + }); }; export let create; diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index af9f43e03f..0e619526aa 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -3,6 +3,8 @@ import View from '../src/ol/View.js'; import Layer from '../src/ol/layer/Layer.js'; //eslint-disable-next-line import Worker from 'worker-loader!./mvtlayer.worker.js'; +import {compose, create} from '../src/ol/transform.js'; +import {createTransformString} from '../src/ol/render/canvas.js'; const mvtLayerWorker = new Worker(); @@ -19,7 +21,28 @@ function getCircularReplacer() { }; } -let container, canvas; +let container, transformContainer, canvas, workerFrameState, mainThreadFrameState; + +function updateContainerTransform() { + if (workerFrameState) { + const viewState = mainThreadFrameState.viewState; + const renderedViewState = workerFrameState.viewState; + const center = viewState.center; + const resolution = viewState.resolution; + const rotation = viewState.rotation; + const renderedCenter = renderedViewState.center; + const renderedResolution = renderedViewState.resolution; + const renderedRotation = renderedViewState.rotation; + const transform = compose(create(), + (renderedCenter[0] - center[0]) / resolution, + (center[1] - renderedCenter[1]) / resolution, + renderedResolution / resolution, renderedResolution / resolution, + rotation - renderedRotation, + 0, 0); + transformContainer.style.transform = createTransformString(transform); + } + +} const map = new Map({ layers: [ @@ -30,16 +53,19 @@ const map = new Map({ container.style.position = 'absolute'; container.style.width = '100%'; container.style.height = '100%'; + transformContainer = document.createElement('div'); + transformContainer.style.position = 'absolute'; + transformContainer.style.width = '100%'; + transformContainer.style.height = '100%'; + container.appendChild(transformContainer); canvas = document.createElement('canvas'); canvas.style.position = 'absolute'; canvas.style.left = '0'; canvas.style.transformOrigin = 'top left'; - container.appendChild(canvas); - const offscreen = canvas.transferControlToOffscreen(); - mvtLayerWorker.postMessage({ - canvas: offscreen - }, [offscreen]); + transformContainer.appendChild(canvas); } + mainThreadFrameState = frameState; + updateContainerTransform(); mvtLayerWorker.postMessage({ frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) }); @@ -53,11 +79,18 @@ const map = new Map({ zoom: 2 }) }); -mvtLayerWorker.addEventListener('message', message => { - if (message.data.type === 'render') { +mvtLayerWorker.addEventListener('message', function(message) { + if (message.data.type === 'request-render') { map.render(); - } else if (canvas && message.data.type === 'transform-opacity') { - canvas.style.transform = message.data.transform; + } else if (canvas && message.data.type === 'rendered') { + transformContainer.style.transform = ''; + const imageData = message.data.imageData; + canvas.width = imageData.width; + canvas.height = imageData.height; + canvas.getContext('2d').drawImage(imageData, 0, 0); canvas.style.opacity = message.data.opacity; + canvas.style.transform = message.data.transform; + workerFrameState = message.data.frameState; + updateContainerTransform(); } }); From bb1ca76bcce6052f732fe117cd854d82479d9b40 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 16 Mar 2020 23:22:49 +0100 Subject: [PATCH 043/119] Make Executor work in workers --- src/ol/render/canvas/Executor.js | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/ol/render/canvas/Executor.js b/src/ol/render/canvas/Executor.js index ccdf260033..c9217a7ac4 100644 --- a/src/ol/render/canvas/Executor.js +++ b/src/ol/render/canvas/Executor.js @@ -18,6 +18,7 @@ import { } from '../../transform.js'; import {defaultTextAlign, measureTextHeight, measureAndCacheTextWidth, measureTextWidths} from '../canvas.js'; import RBush from 'rbush/rbush.js'; +import {WINDOW} from '../../has.js'; /** @@ -204,7 +205,9 @@ class Executor { contextInstructions.push('lineCap', strokeState.lineCap); contextInstructions.push('lineJoin', strokeState.lineJoin); contextInstructions.push('miterLimit', strokeState.miterLimit); - if (CanvasRenderingContext2D.prototype.setLineDash) { + // eslint-disable-next-line + const Context = WINDOW ? CanvasRenderingContext2D : OffscreenCanvasRenderingContext2D; + if (Context.prototype.setLineDash) { contextInstructions.push('setLineDash', [strokeState.lineDash]); contextInstructions.push('lineDashOffset', strokeState.lineDashOffset); } From 06f6ba13c888242168c23c3ca1c97b8962e5a055 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 16 Mar 2020 23:23:34 +0100 Subject: [PATCH 044/119] Make font loading work in workers --- src/ol/css.js | 27 ++++++++++++------------ src/ol/render/canvas.js | 46 ++++++++++++++++++++++++++++++++++------- 2 files changed, 53 insertions(+), 20 deletions(-) diff --git a/src/ol/css.js b/src/ol/css.js index c855fae7ea..f4eb09eb59 100644 --- a/src/ol/css.js +++ b/src/ol/css.js @@ -7,6 +7,7 @@ * @property {Array} families * @property {string} style * @property {string} weight + * @property {string} lineHeight */ @@ -68,8 +69,9 @@ export const CLASS_COLLAPSED = 'ol-collapsed'; /** * Get the list of font families from a font spec. Note that this doesn't work * for font families that have commas in them. - * @param {string} The CSS font property. - * @return {FontParameters} The font families (or null if the input spec is invalid). + * @param {string} fontSpec The CSS font property. + * @param {function(FontParameters):void} callback Called with the font families + * (or null if the input spec is invalid). */ export const getFontParameters = (function() { /** @@ -80,26 +82,25 @@ export const getFontParameters = (function() { * @type {Object} */ const cache = {}; - return function(font) { + return function(fontSpec, callback) { if (!style) { style = document.createElement('div').style; } - if (!(font in cache)) { - style.font = font; + if (!(fontSpec in cache)) { + style.font = fontSpec; const family = style.fontFamily; - const fontWeight = style.fontWeight; - const fontStyle = style.fontStyle; - style.font = ''; if (!family) { - return null; + callback(null); } const families = family.split(/,\s?/); - cache[font] = { + cache[fontSpec] = { families: families, - weight: fontWeight, - style: fontStyle + weight: style.fontWeight, + style: style.fontStyle, + lineHeight: style.lineHeight }; + style.font = ''; } - return cache[font]; + callback(cache[fontSpec]); }; })(); diff --git a/src/ol/render/canvas.js b/src/ol/render/canvas.js index 04781b9bc1..1a5293bd2e 100644 --- a/src/ol/render/canvas.js +++ b/src/ol/render/canvas.js @@ -266,8 +266,7 @@ export const registerFont = (function() { } } - return function(fontSpec) { - const font = getFontParameters(fontSpec); + function fontCallback(font) { if (!font) { return; } @@ -285,6 +284,31 @@ export const registerFont = (function() { } } } + } + + return function(fontSpec) { + if (WINDOW) { + getFontParameters(fontSpec, fontCallback); + } else { + /** @type {any} */ + const worker = self; + worker.postMessage({ + type: 'getFontParameters', + font: fontSpec + }); + worker.addEventListener('message', function handler(event) { + if (event.data.type === 'getFontParameters') { + worker.removeEventListener('message', handler); + const font = event.data.font; + fontCallback(font); + if (!textHeights[fontSpec]) { + const metrics = measureText(fontSpec, 'Žg'); + const lineHeight = isNaN(font.lineHeight) ? 1.2 : Number(font.lineHeight); + textHeights[fontSpec] = lineHeight * (metrics.actualBoundingBoxAscent + metrics.actualBoundingBoxDescent); + } + } + }); + } }; })(); @@ -320,13 +344,12 @@ export const measureTextHeight = (function() { }; })(); - /** * @param {string} font Font. * @param {string} text Text. - * @return {number} Width. + * @return {TextMetrics} Text metrics. */ -export function measureTextWidth(font, text) { +function measureText(font, text) { if (!measureContext) { measureContext = createCanvasContext2D(1, 1); } @@ -334,7 +357,16 @@ export function measureTextWidth(font, text) { measureContext.font = font; measureFont = measureContext.font; } - return measureContext.measureText(text).width; + return measureContext.measureText(text); +} + +/** + * @param {string} font Font. + * @param {string} text Text. + * @return {number} Width. + */ +export function measureTextWidth(font, text) { + return measureText(font, text).width; } @@ -434,7 +466,7 @@ function executeLabelInstructions(label, context) { const contextInstructions = label.contextInstructions; for (let i = 0, ii = contextInstructions.length; i < ii; i += 2) { if (Array.isArray(contextInstructions[i + 1])) { - CanvasRenderingContext2D.prototype[contextInstructions[i]].apply(context, contextInstructions[i + 1]); + context[contextInstructions[i]].apply(context, contextInstructions[i + 1]); } else { context[contextInstructions[i]] = contextInstructions[i + 1]; } From 10c333058042ae979e476076ef0892bffb32839a Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 16 Mar 2020 23:26:09 +0100 Subject: [PATCH 045/119] Use correct transorms at the right time --- examples/mvtlayer.worker.js | 31 ++++++++++++++++++------------- 1 file changed, 18 insertions(+), 13 deletions(-) diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js index bc2ab5a20b..cf535c89ba 100644 --- a/examples/mvtlayer.worker.js +++ b/examples/mvtlayer.worker.js @@ -4,6 +4,7 @@ import MVT from '../src/ol/format/MVT.js'; import {Projection} from '../src/ol/proj.js'; import TileQueue from '../src/ol/TileQueue.js'; import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; +import {renderDeclutterItems} from '../src/ol/render.js'; const key = 'pk.eyJ1IjoiYWhvY2V2YXIiLCJhIjoiY2pzbmg0Nmk5MGF5NzQzbzRnbDNoeHJrbiJ9.7_-_gL8ur7ZtEiNwRfCy7Q'; @@ -45,7 +46,7 @@ const tileQueue = new TileQueue(getTilePriority, function() { const maxTotalLoading = 8; const maxNewLoads = 2; - +let rendererTransform, rendererOpacity; renderer.useContainer = function(target, transform, opacity) { target.style = {}; this.canvas = target; @@ -53,21 +54,16 @@ renderer.useContainer = function(target, transform, opacity) { this.container = { firstElementChild: target }; - layer.once('postrender', function() { - const imageData = canvas.transferToImageBitmap(); - worker.postMessage({ - type: 'rendered', - imageData: imageData, - transform: transform, - opacity: opacity, - frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) - }, [imageData]); - }); + rendererTransform = transform; + rendererOpacity = opacity; }; let rendering = false; -worker.onmessage = function(event) { +worker.addEventListener('message', function(event) { + if (event.data.type !== 'render') { + return; + } if (rendering) { // drop this frame worker.postMessage({type: 'request-render'}); @@ -79,12 +75,21 @@ worker.onmessage = function(event) { rendering = true; requestAnimationFrame(function() { renderer.renderFrame(frameState, canvas); + renderDeclutterItems(frameState, null); if (tileQueue.getTilesLoading() < maxTotalLoading) { tileQueue.reprioritize(); // FIXME only call if view has changed tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); } + const imageData = canvas.transferToImageBitmap(); + worker.postMessage({ + type: 'rendered', + imageData: imageData, + transform: rendererTransform, + opacity: rendererOpacity, + frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + }, [imageData]); rendering = false; }); -}; +}); export let create; From 3217bf131636da5353b88b6189e358c6e08a4fd5 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 16 Mar 2020 23:26:24 +0100 Subject: [PATCH 046/119] Add style handling --- examples/mvtlayer.worker.js | 3 ++ examples/offscreen-canvas-tiles.css | 3 ++ examples/offscreen-canvas-tiles.js | 31 ++++++++++++++++ examples/resources/mapbox-streets-v6-style.js | 36 ++++++++++++++++--- 4 files changed, 68 insertions(+), 5 deletions(-) create mode 100644 examples/offscreen-canvas-tiles.css diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js index cf535c89ba..7dc263cf23 100644 --- a/examples/mvtlayer.worker.js +++ b/examples/mvtlayer.worker.js @@ -4,6 +4,8 @@ import MVT from '../src/ol/format/MVT.js'; import {Projection} from '../src/ol/proj.js'; import TileQueue from '../src/ol/TileQueue.js'; import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; +import {Style, Fill, Stroke, Icon, Text} from '../src/ol/style.js'; +import createMapboxStreetsV6Style from './resources/mapbox-streets-v6-style.js'; import {renderDeclutterItems} from '../src/ol/render.js'; const key = 'pk.eyJ1IjoiYWhvY2V2YXIiLCJhIjoiY2pzbmg0Nmk5MGF5NzQzbzRnbDNoeHJrbiJ9.7_-_gL8ur7ZtEiNwRfCy7Q'; @@ -33,6 +35,7 @@ function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { const layer = new VectorTileLayer({ declutter: true, + style: createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text), source: new VectorTileSource({ format: new MVT(), url: 'https://{a-d}.tiles.mapbox.com/v4/mapbox.mapbox-streets-v6/' + diff --git a/examples/offscreen-canvas-tiles.css b/examples/offscreen-canvas-tiles.css new file mode 100644 index 0000000000..33e90f7301 --- /dev/null +++ b/examples/offscreen-canvas-tiles.css @@ -0,0 +1,3 @@ +.map { + background: #f8f4f0; +} diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index 0e619526aa..356e9ead4c 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -5,9 +5,39 @@ import Layer from '../src/ol/layer/Layer.js'; import Worker from 'worker-loader!./mvtlayer.worker.js'; import {compose, create} from '../src/ol/transform.js'; import {createTransformString} from '../src/ol/render/canvas.js'; +import {getFontParameters} from '../src/ol/css.js'; const mvtLayerWorker = new Worker(); +const loadingImages = {}; +mvtLayerWorker.addEventListener('message', event => { + if (event.data.type === 'getFontParameters') { + getFontParameters(event.data.font, font => { + mvtLayerWorker.postMessage({ + type: 'getFontParameters', + font: font + }); + }); + } else if (event.data.type === 'loadImage') { + if (!(event.data.src in loadingImages)) { + const image = new Image(); + image.crossOrigin = 'anonymous'; + image.addEventListener('load', function() { + createImageBitmap(image, 0, 0, image.width, image.height).then(imageBitmap => { + delete loadingImages[event.data.iconName]; + mvtLayerWorker.postMessage({ + type: 'imageLoaded', + image: imageBitmap, + iconName: event.data.iconName + }, [imageBitmap]); + }); + }); + image.src = 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + event.data.iconName + '-15.svg'; + loadingImages[event.data.iconName] = true; + } + } +}); + function getCircularReplacer() { const seen = new WeakSet(); return function(key, value) { @@ -67,6 +97,7 @@ const map = new Map({ mainThreadFrameState = frameState; updateContainerTransform(); mvtLayerWorker.postMessage({ + type: 'render', frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) }); return container; diff --git a/examples/resources/mapbox-streets-v6-style.js b/examples/resources/mapbox-streets-v6-style.js index abd5babca3..e1f0197bf8 100644 --- a/examples/resources/mapbox-streets-v6-style.js +++ b/examples/resources/mapbox-streets-v6-style.js @@ -2,6 +2,20 @@ // http://a.tiles.mapbox.com/v4/mapbox.mapbox-streets-v6.json function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { + + let worker; + try { + worker = self.document ? null : self; + worker.addEventListener('message', message => { + if (message.data.type === 'imageLoaded') { + iconCache[message.data.iconName].setImage(new Icon({ + img: message.data.image, + imgSize: [15, 15] + })); + } + }); + } catch (e) {} + var fill = new Fill({color: ''}); var stroke = new Stroke({color: '', width: 1}); var polygon = new Style({fill: fill}); @@ -14,11 +28,19 @@ function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { function getIcon(iconName) { var icon = iconCache[iconName]; if (!icon) { - icon = new Style({image: new Icon({ - src: 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + iconName + '-15.svg', - imgSize: [15, 15], - crossOrigin: 'anonymous' - })}); + if (!worker) { + icon = new Style({image: new Icon({ + src: 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + iconName + '-15.svg', + imgSize: [15, 15], + crossOrigin: 'anonymous' + })}); + } else { + icon = new Style({}); + worker.postMessage({ + type: 'loadImage', + iconName: iconName + }); + } iconCache[iconName] = icon; } return icon; @@ -310,3 +332,7 @@ function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { return styles; }; } + +try { + module.exports = createMapboxStreetsV6Style; +} catch (e) {} From f80c175263be43b0e4c8110ae090701d42d1d039 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Tue, 17 Mar 2020 16:43:50 +0100 Subject: [PATCH 047/119] Do not transform rotated views --- examples/offscreen-canvas-tiles.js | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index 356e9ead4c..13899f2949 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -63,12 +63,15 @@ function updateContainerTransform() { const renderedCenter = renderedViewState.center; const renderedResolution = renderedViewState.resolution; const renderedRotation = renderedViewState.rotation; - const transform = compose(create(), - (renderedCenter[0] - center[0]) / resolution, - (center[1] - renderedCenter[1]) / resolution, - renderedResolution / resolution, renderedResolution / resolution, - rotation - renderedRotation, - 0, 0); + const transform = create(); + if (!rotation) { + compose(transform, + (renderedCenter[0] - center[0]) / resolution, + (center[1] - renderedCenter[1]) / resolution, + renderedResolution / resolution, renderedResolution / resolution, + rotation - renderedRotation, + 0, 0); + } transformContainer.style.transform = createTransformString(transform); } From 6dcc54bfb89f39a8c8b9576eb3a943db60121a5e Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Tue, 17 Mar 2020 17:55:54 +0100 Subject: [PATCH 048/119] 'action' instead of 'type' as message identifier --- examples/mvtlayer.worker.js | 8 ++-- examples/offscreen-canvas-tiles.js | 65 ++++++++++++++++-------------- src/ol/render/canvas.js | 6 +-- 3 files changed, 41 insertions(+), 38 deletions(-) diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js index 7dc263cf23..16a555e052 100644 --- a/examples/mvtlayer.worker.js +++ b/examples/mvtlayer.worker.js @@ -44,7 +44,7 @@ const layer = new VectorTileLayer({ }); const renderer = layer.getRenderer(); const tileQueue = new TileQueue(getTilePriority, function() { - worker.postMessage({type: 'request-render'}); + worker.postMessage({action: 'request-render'}); }); const maxTotalLoading = 8; const maxNewLoads = 2; @@ -64,12 +64,12 @@ renderer.useContainer = function(target, transform, opacity) { let rendering = false; worker.addEventListener('message', function(event) { - if (event.data.type !== 'render') { + if (event.data.action !== 'render') { return; } if (rendering) { // drop this frame - worker.postMessage({type: 'request-render'}); + worker.postMessage({action: 'request-render'}); return; } frameState = event.data.frameState; @@ -85,7 +85,7 @@ worker.addEventListener('message', function(event) { } const imageData = canvas.transferToImageBitmap(); worker.postMessage({ - type: 'rendered', + action: 'rendered', imageData: imageData, transform: rendererTransform, opacity: rendererOpacity, diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index 13899f2949..60ee70480c 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -11,14 +11,14 @@ const mvtLayerWorker = new Worker(); const loadingImages = {}; mvtLayerWorker.addEventListener('message', event => { - if (event.data.type === 'getFontParameters') { + if (event.data.action === 'getFontParameters') { getFontParameters(event.data.font, font => { mvtLayerWorker.postMessage({ - type: 'getFontParameters', + action: 'getFontParameters', font: font }); }); - } else if (event.data.type === 'loadImage') { + } else if (event.data.action === 'loadImage') { if (!(event.data.src in loadingImages)) { const image = new Image(); image.crossOrigin = 'anonymous'; @@ -26,7 +26,7 @@ mvtLayerWorker.addEventListener('message', event => { createImageBitmap(image, 0, 0, image.width, image.height).then(imageBitmap => { delete loadingImages[event.data.iconName]; mvtLayerWorker.postMessage({ - type: 'imageLoaded', + action: 'imageLoaded', image: imageBitmap, iconName: event.data.iconName }, [imageBitmap]); @@ -77,34 +77,37 @@ function updateContainerTransform() { } +function render(id, frameState) { + if (!container) { + container = document.createElement('div'); + container.style.position = 'absolute'; + container.style.width = '100%'; + container.style.height = '100%'; + transformContainer = document.createElement('div'); + transformContainer.style.position = 'absolute'; + transformContainer.style.width = '100%'; + transformContainer.style.height = '100%'; + container.appendChild(transformContainer); + canvas = document.createElement('canvas'); + canvas.style.position = 'absolute'; + canvas.style.left = '0'; + canvas.style.transformOrigin = 'top left'; + transformContainer.appendChild(canvas); + } + mainThreadFrameState = frameState; + updateContainerTransform(); + mvtLayerWorker.postMessage({ + action: 'render', + id: id, + frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + }); + return container; +} + const map = new Map({ layers: [ new Layer({ - render: function(frameState) { - if (!container) { - container = document.createElement('div'); - container.style.position = 'absolute'; - container.style.width = '100%'; - container.style.height = '100%'; - transformContainer = document.createElement('div'); - transformContainer.style.position = 'absolute'; - transformContainer.style.width = '100%'; - transformContainer.style.height = '100%'; - container.appendChild(transformContainer); - canvas = document.createElement('canvas'); - canvas.style.position = 'absolute'; - canvas.style.left = '0'; - canvas.style.transformOrigin = 'top left'; - transformContainer.appendChild(canvas); - } - mainThreadFrameState = frameState; - updateContainerTransform(); - mvtLayerWorker.postMessage({ - type: 'render', - frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) - }); - return container; - } + render: render.bind(undefined, 'mapbox') }) ], target: 'map', @@ -114,9 +117,9 @@ const map = new Map({ }) }); mvtLayerWorker.addEventListener('message', function(message) { - if (message.data.type === 'request-render') { + if (message.data.action === 'request-render') { map.render(); - } else if (canvas && message.data.type === 'rendered') { + } else if (canvas && message.data.action === 'rendered') { transformContainer.style.transform = ''; const imageData = message.data.imageData; canvas.width = imageData.width; diff --git a/src/ol/render/canvas.js b/src/ol/render/canvas.js index 1a5293bd2e..002ec4efd0 100644 --- a/src/ol/render/canvas.js +++ b/src/ol/render/canvas.js @@ -289,15 +289,15 @@ export const registerFont = (function() { return function(fontSpec) { if (WINDOW) { getFontParameters(fontSpec, fontCallback); - } else { + } else if (self.postMessage) { /** @type {any} */ const worker = self; worker.postMessage({ - type: 'getFontParameters', + action: 'getFontParameters', font: fontSpec }); worker.addEventListener('message', function handler(event) { - if (event.data.type === 'getFontParameters') { + if (event.data.action === 'getFontParameters') { worker.removeEventListener('message', handler); const font = event.data.font; fontCallback(font); From 3f7f999db02e52e2bbd27ef4aab960517e1f56f2 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sat, 21 Mar 2020 15:49:01 +0100 Subject: [PATCH 049/119] Avoid try/catch, DOM and workers --- src/ol/css.js | 79 +++++++++++++++++++------------- src/ol/dom.js | 8 ++-- src/ol/has.js | 20 ++------ src/ol/render/canvas.js | 72 +++++++++++------------------ src/ol/render/canvas/Executor.js | 4 +- tsconfig.json | 2 +- 6 files changed, 85 insertions(+), 100 deletions(-) diff --git a/src/ol/css.js b/src/ol/css.js index f4eb09eb59..88a6d5c9dc 100644 --- a/src/ol/css.js +++ b/src/ol/css.js @@ -4,10 +4,13 @@ /** * @typedef {Object} FontParameters - * @property {Array} families * @property {string} style + * @property {string} variant * @property {string} weight + * @property {string} size * @property {string} lineHeight + * @property {string} family + * @property {Array} families */ @@ -65,42 +68,52 @@ export const CLASS_CONTROL = 'ol-control'; */ export const CLASS_COLLAPSED = 'ol-collapsed'; +/** + * From http://stackoverflow.com/questions/10135697/regex-to-parse-any-css-font + * @type {RegExp} + */ +const fontRegEx = new RegExp([ + '^\\s*(?=(?:(?:[-a-z]+\\s*){0,2}(italic|oblique))?)', + '(?=(?:(?:[-a-z]+\\s*){0,2}(small-caps))?)', + '(?=(?:(?:[-a-z]+\\s*){0,2}(bold(?:er)?|lighter|[1-9]00 ))?)', + '(?:(?:normal|\\1|\\2|\\3)\\s*){0,3}((?:xx?-)?', + '(?:small|large)|medium|smaller|larger|[\\.\\d]+(?:\\%|in|[cem]m|ex|p[ctx]))', + '(?:\\s*\\/\\s*(normal|[\\.\\d]+(?:\\%|in|[cem]m|ex|p[ctx])?))', + '?\\s*([-,\\"\\\'\\sa-z]+?)\\s*$' +].join(''), 'i'); +const fontRegExMatchIndex = [ + 'style', + 'variant', + 'weight', + 'size', + 'lineHeight', + 'family' +]; /** * Get the list of font families from a font spec. Note that this doesn't work * for font families that have commas in them. * @param {string} fontSpec The CSS font property. - * @param {function(FontParameters):void} callback Called with the font families - * (or null if the input spec is invalid). + * @return {FontParameters} The font parameters (or null if the input spec is invalid). */ -export const getFontParameters = (function() { - /** - * @type {CSSStyleDeclaration} - */ - let style; - /** - * @type {Object} - */ - const cache = {}; - return function(fontSpec, callback) { - if (!style) { - style = document.createElement('div').style; +export const getFontParameters = function(fontSpec) { + const match = fontSpec.match(fontRegEx); + if (!match) { + return null; + } + const style = /** @type {FontParameters} */ ({ + lineHeight: 'normal', + size: '1.2em', + style: 'normal', + weight: 'normal', + variant: 'normal' + }); + for (let i = 0, ii = fontRegExMatchIndex.length; i < ii; ++i) { + const value = match[i + 1]; + if (value !== undefined) { + style[fontRegExMatchIndex[i]] = value; } - if (!(fontSpec in cache)) { - style.font = fontSpec; - const family = style.fontFamily; - if (!family) { - callback(null); - } - const families = family.split(/,\s?/); - cache[fontSpec] = { - families: families, - weight: style.fontWeight, - style: style.fontStyle, - lineHeight: style.lineHeight - }; - style.font = ''; - } - callback(cache[fontSpec]); - }; -})(); + } + style.families = style.family.split(/,\s?/); + return style; +}; diff --git a/src/ol/dom.js b/src/ol/dom.js index 37d188541e..e3c403cc99 100644 --- a/src/ol/dom.js +++ b/src/ol/dom.js @@ -1,3 +1,5 @@ +import {WORKER_OFFSCREEN_CANVAS} from './has.js'; + /** * @module ol/dom */ @@ -14,9 +16,9 @@ export function createCanvasContext2D(opt_width, opt_height, opt_canvasPool) { const canvas = opt_canvasPool && opt_canvasPool.length ? opt_canvasPool.shift() : - 'document' in self ? - document.createElement('canvas') : - new OffscreenCanvas(opt_width || 300, opt_height || 300); + WORKER_OFFSCREEN_CANVAS ? + new OffscreenCanvas(opt_width || 300, opt_height || 300) : + document.createElement('canvas'); if (opt_width) { canvas.width = opt_width; } diff --git a/src/ol/has.js b/src/ol/has.js index 24b053a2fe..3fdebf833c 100644 --- a/src/ol/has.js +++ b/src/ol/has.js @@ -37,27 +37,15 @@ export const MAC = ua.indexOf('macintosh') !== -1; * @type {number} * @api */ -export const DEVICE_PIXEL_RATIO = (function() { - try { - return self.devicePixelRatio; - } catch (e) { - return window.devicePixelRatio || 1; - } -})(); +export const DEVICE_PIXEL_RATIO = (typeof self !== 'undefined' ? self.devicePixelRatio : window.devicePixelRatio) || 1; /** - * The execution context is a window. + * The execution context is a worker with OffscreenCanvas available. * @const * @type {boolean} */ -export const WINDOW = (function() { - try { - return 'document' in self; - } catch (e) { - // ancient browsers don't have `self` - return true; - } -})(); +export const WORKER_OFFSCREEN_CANVAS = typeof WorkerGlobalScope !== 'undefined' && typeof OffscreenCanvas !== 'undefined' && + self instanceof WorkerGlobalScope; //eslint-disable-line /** * Image.prototype.decode() is supported. diff --git a/src/ol/render/canvas.js b/src/ol/render/canvas.js index 002ec4efd0..edd5737a07 100644 --- a/src/ol/render/canvas.js +++ b/src/ol/render/canvas.js @@ -6,7 +6,7 @@ import {createCanvasContext2D} from '../dom.js'; import {clear} from '../obj.js'; import BaseObject from '../Object.js'; import EventTarget from '../events/Target.js'; -import {WINDOW} from '../has.js'; +import {WORKER_OFFSCREEN_CANVAS} from '../has.js'; import {toString} from '../transform.js'; @@ -266,7 +266,8 @@ export const registerFont = (function() { } } - function fontCallback(font) { + return function(fontSpec) { + const font = getFontParameters(fontSpec); if (!font) { return; } @@ -284,31 +285,6 @@ export const registerFont = (function() { } } } - } - - return function(fontSpec) { - if (WINDOW) { - getFontParameters(fontSpec, fontCallback); - } else if (self.postMessage) { - /** @type {any} */ - const worker = self; - worker.postMessage({ - action: 'getFontParameters', - font: fontSpec - }); - worker.addEventListener('message', function handler(event) { - if (event.data.action === 'getFontParameters') { - worker.removeEventListener('message', handler); - const font = event.data.font; - fontCallback(font); - if (!textHeights[fontSpec]) { - const metrics = measureText(fontSpec, 'Žg'); - const lineHeight = isNaN(font.lineHeight) ? 1.2 : Number(font.lineHeight); - textHeights[fontSpec] = lineHeight * (metrics.actualBoundingBoxAscent + metrics.actualBoundingBoxDescent); - } - } - }); - } }; })(); @@ -323,22 +299,29 @@ export const measureTextHeight = (function() { */ let div; const heights = textHeights; - return function(font) { - let height = heights[font]; + return function(fontSpec) { + let height = heights[fontSpec]; if (height == undefined) { - if (!div) { - div = document.createElement('div'); - div.innerHTML = 'M'; - div.style.margin = '0 !important'; - div.style.padding = '0 !important'; - div.style.position = 'absolute !important'; - div.style.left = '-99999px !important'; + if (WORKER_OFFSCREEN_CANVAS) { + const font = getFontParameters(fontSpec); + const metrics = measureText(fontSpec, 'Žg'); + const lineHeight = isNaN(Number(font.lineHeight)) ? 1.2 : Number(font.lineHeight); + textHeights[fontSpec] = lineHeight * (metrics.actualBoundingBoxAscent + metrics.actualBoundingBoxDescent); + } else { + if (!div) { + div = document.createElement('div'); + div.innerHTML = 'M'; + div.style.margin = '0 !important'; + div.style.padding = '0 !important'; + div.style.position = 'absolute !important'; + div.style.left = '-99999px !important'; + } + div.style.font = fontSpec; + document.body.appendChild(div); + height = div.offsetHeight; + heights[fontSpec] = height; + document.body.removeChild(div); } - div.style.font = font; - document.body.appendChild(div); - height = div.offsetHeight; - heights[font] = height; - document.body.removeChild(div); } return height; }; @@ -369,7 +352,6 @@ export function measureTextWidth(font, text) { return measureText(font, text).width; } - /** * Measure text width using a cache. * @param {string} font The font. @@ -484,13 +466,13 @@ let createTransformStringCanvas = null; * @return {string} CSS transform. */ export function createTransformString(transform) { - if (WINDOW) { + if (WORKER_OFFSCREEN_CANVAS) { + return toString(transform); + } else { if (!createTransformStringCanvas) { createTransformStringCanvas = createCanvasContext2D(1, 1).canvas; } createTransformStringCanvas.style.transform = toString(transform); return createTransformStringCanvas.style.transform; - } else { - return toString(transform); } } diff --git a/src/ol/render/canvas/Executor.js b/src/ol/render/canvas/Executor.js index c9217a7ac4..5f88e0aa94 100644 --- a/src/ol/render/canvas/Executor.js +++ b/src/ol/render/canvas/Executor.js @@ -18,7 +18,7 @@ import { } from '../../transform.js'; import {defaultTextAlign, measureTextHeight, measureAndCacheTextWidth, measureTextWidths} from '../canvas.js'; import RBush from 'rbush/rbush.js'; -import {WINDOW} from '../../has.js'; +import {WORKER_OFFSCREEN_CANVAS} from '../../has.js'; /** @@ -206,7 +206,7 @@ class Executor { contextInstructions.push('lineJoin', strokeState.lineJoin); contextInstructions.push('miterLimit', strokeState.miterLimit); // eslint-disable-next-line - const Context = WINDOW ? CanvasRenderingContext2D : OffscreenCanvasRenderingContext2D; + const Context = WORKER_OFFSCREEN_CANVAS ? OffscreenCanvasRenderingContext2D : CanvasRenderingContext2D; if (Context.prototype.setLineDash) { contextInstructions.push('setLineDash', [strokeState.lineDash]); contextInstructions.push('lineDashOffset', strokeState.lineDashOffset); diff --git a/tsconfig.json b/tsconfig.json index 438785ff84..3a208514a3 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -3,7 +3,7 @@ /* Basic Options */ "target": "ES2017", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017','ES2018' or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */ - "lib": ["es2017", "dom"], /* Specify library files to be included in the compilation. */ + "lib": ["es2017", "dom", "webworker"], /* Specify library files to be included in the compilation. */ "allowJs": true, /* Allow javascript files to be compiled. */ "checkJs": true, /* Report errors in .js files. */ // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */ From b9bfe45d86b0e4d70f5c0e9129ccb70915c54499 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:04:53 +0100 Subject: [PATCH 050/119] Update ol-mapbox-style --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index d9adcfa006..67d75abf99 100644 --- a/package.json +++ b/package.json @@ -83,7 +83,7 @@ "loglevelnext": "^3.0.1", "marked": "0.8.2", "mocha": "7.1.1", - "ol-mapbox-style": "^6.0.0", + "ol-mapbox-style": "^6.1.0", "pixelmatch": "^5.1.0", "pngjs": "^3.4.0", "proj4": "2.6.0", From 30ac91c4aefd0a644a7ccae19a32a9eb7499b38c Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:05:27 +0100 Subject: [PATCH 051/119] Simpler feature check --- src/ol/has.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/has.js b/src/ol/has.js index 3fdebf833c..6452b79a58 100644 --- a/src/ol/has.js +++ b/src/ol/has.js @@ -37,7 +37,7 @@ export const MAC = ua.indexOf('macintosh') !== -1; * @type {number} * @api */ -export const DEVICE_PIXEL_RATIO = (typeof self !== 'undefined' ? self.devicePixelRatio : window.devicePixelRatio) || 1; +export const DEVICE_PIXEL_RATIO = typeof devicePixelRatio !== 'undefined' ? devicePixelRatio : 1; /** * The execution context is a worker with OffscreenCanvas available. From bc1be50cbc5a3becfd698ba15963359123262766 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:06:03 +0100 Subject: [PATCH 052/119] Add worker support to examples --- examples/resources/common.js | 36 ++++++++++++++++++----------- examples/templates/example.html | 9 +++++++- examples/webpack/example-builder.js | 30 +++++++++++++++++++++++- 3 files changed, 59 insertions(+), 16 deletions(-) diff --git a/examples/resources/common.js b/examples/resources/common.js index 893fe51c1a..a59685d3d5 100644 --- a/examples/resources/common.js +++ b/examples/resources/common.js @@ -57,6 +57,8 @@ event.preventDefault(); const html = document.getElementById('example-html-source').innerText; const js = document.getElementById('example-js-source').innerText; + const workerContainer = document.getElementById('example-worker-source'); + const worker = workerContainer ? workerContainer.innerText : undefined; const pkgJson = document.getElementById('example-pkg-source').innerText; const form = document.getElementById('codepen-form'); @@ -68,22 +70,28 @@ Promise.all(promises) .then(results => { - const data = { - files: { - 'index.html': { - content: html - }, - 'index.js': { - content: js - }, - "package.json": { - content: pkgJson - }, - 'sandbox.config.json': { - content: '{"template": "parcel"}' - } + const files = { + 'index.html': { + content: html + }, + 'index.js': { + content: js + }, + "package.json": { + content: pkgJson + }, + 'sandbox.config.json': { + content: '{"template": "parcel"}' } }; + if (worker) { + files['worker.js'] = { + content: worker + } + } + const data = { + files: files + }; for (let i = 0; i < localResources.length; i++) { data.files[localResources[i]] = results[i]; diff --git a/examples/templates/example.html b/examples/templates/example.html index a45f88e7be..b0c5cee4b7 100644 --- a/examples/templates/example.html +++ b/examples/templates/example.html @@ -160,6 +160,14 @@
index.jsimport 'ol/ol.css';
 {{ js.source }}
+{{#if worker.source}} +
+
+ Copy +
+
worker.js{{ worker.source }}
+
+{{/if}}
Copy @@ -167,7 +175,6 @@
package.json{{ pkgJson }}
- {{{ js.tag }}} diff --git a/examples/webpack/example-builder.js b/examples/webpack/example-builder.js index 22a7867500..d25306b897 100644 --- a/examples/webpack/example-builder.js +++ b/examples/webpack/example-builder.js @@ -208,6 +208,10 @@ ExampleBuilder.prototype.render = async function(dir, chunk) { jsSource = jsSource.replace(new RegExp(entry.key, 'g'), entry.value); } } + // Remove worker loader import and modify `new Worker()` to add source + jsSource = jsSource.replace(/import Worker from 'worker-loader![^\n]*\n/g, ''); + jsSource = jsSource.replace('new Worker()', 'new Worker(\'./worker.js\')'); + data.js = { tag: ``, source: jsSource @@ -218,9 +222,33 @@ ExampleBuilder.prototype.render = async function(dir, chunk) { data.js.tag = prelude + data.js.tag; } + // check for worker js + const workerName = `${name}.worker.js`; + const workerPath = path.join(dir, workerName); + let workerSource; + try { + workerSource = await readFile(workerPath, readOptions); + } catch (err) { + // pass + } + if (workerSource) { + // remove "../src/" prefix and ".js" to have the same import syntax as the documentation + workerSource = workerSource.replace(/'\.\.\/src\//g, '\''); + workerSource = workerSource.replace(/\.js';/g, '\';'); + if (data.cloak) { + for (const entry of data.cloak) { + workerSource = workerSource.replace(new RegExp(entry.key, 'g'), entry.value); + } + } + data.worker = { + source: workerSource + }; + assets[workerName] = workerSource; + } + data.pkgJson = JSON.stringify({ name: name, - dependencies: getDependencies(jsSource), + dependencies: getDependencies(jsSource + workerSource ? `\n${workerSource}` : ''), devDependencies: { parcel: '1.11.0' }, From ade9ac8857685508edb3abf8d9cd517494a23e2f Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:08:24 +0100 Subject: [PATCH 053/119] Make mapbox-style example fullscreen on demand --- examples/mapbox-style.html | 27 ++------------------------- examples/mapbox-style.js | 5 ++++- 2 files changed, 6 insertions(+), 26 deletions(-) diff --git a/examples/mapbox-style.html b/examples/mapbox-style.html index 8285734955..1c88215464 100644 --- a/examples/mapbox-style.html +++ b/examples/mapbox-style.html @@ -1,5 +1,5 @@ --- -layout: example-verbatim.html +layout: example.html title: Vector tiles created from a Mapbox Style object shortdesc: Example of using ol-mapbox-style with tiles from maptiler.com. docs: > @@ -10,27 +10,4 @@ cloak: - key: get_your_own_D6rA4zTHduk6KOKTXzGB value: Get your own API key at https://www.maptiler.com/cloud/ --- - - - - - - - Mapbox Style objects with ol-mapbox-style - - - - - -
- - - - +
diff --git a/examples/mapbox-style.js b/examples/mapbox-style.js index 819177a69d..a774155526 100644 --- a/examples/mapbox-style.js +++ b/examples/mapbox-style.js @@ -1,3 +1,6 @@ import apply from 'ol-mapbox-style'; +import FullScreen from '../src/ol/control/FullScreen.js'; -apply('map', 'https://api.maptiler.com/maps/topo/style.json?key=get_your_own_D6rA4zTHduk6KOKTXzGB'); +apply('map', 'https://api.maptiler.com/maps/topo/style.json?key=get_your_own_D6rA4zTHduk6KOKTXzGB').then(function(map) { + map.addControl(new FullScreen()); +}); From 28f390828dac51b1f793e165356d846187c4178e Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:11:07 +0100 Subject: [PATCH 054/119] Use same data as in mapbox-style example --- examples/mvtlayer.worker.js | 98 ----------- examples/offscreen-canvas-tiles.css | 2 +- examples/offscreen-canvas-tiles.js | 16 +- examples/offscreen-canvas-tiles.worker.js | 154 ++++++++++++++++++ examples/resources/mapbox-streets-v6-style.js | 38 +---- 5 files changed, 170 insertions(+), 138 deletions(-) delete mode 100644 examples/mvtlayer.worker.js create mode 100644 examples/offscreen-canvas-tiles.worker.js diff --git a/examples/mvtlayer.worker.js b/examples/mvtlayer.worker.js deleted file mode 100644 index 16a555e052..0000000000 --- a/examples/mvtlayer.worker.js +++ /dev/null @@ -1,98 +0,0 @@ -import VectorTileLayer from '../src/ol/layer/VectorTile.js'; -import VectorTileSource from '../src/ol/source/VectorTile.js'; -import MVT from '../src/ol/format/MVT.js'; -import {Projection} from '../src/ol/proj.js'; -import TileQueue from '../src/ol/TileQueue.js'; -import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; -import {Style, Fill, Stroke, Icon, Text} from '../src/ol/style.js'; -import createMapboxStreetsV6Style from './resources/mapbox-streets-v6-style.js'; -import {renderDeclutterItems} from '../src/ol/render.js'; - -const key = 'pk.eyJ1IjoiYWhvY2V2YXIiLCJhIjoiY2pzbmg0Nmk5MGF5NzQzbzRnbDNoeHJrbiJ9.7_-_gL8ur7ZtEiNwRfCy7Q'; - -/** @type {any} */ -const worker = self; - -let frameState; -const canvas = new OffscreenCanvas(1, 1); - -function getCircularReplacer() { - const seen = new WeakSet(); - return function(key, value) { - if (typeof value === 'object' && value !== null) { - if (seen.has(value)) { - return '[circular]'; - } - seen.add(value); - } - return value; - }; -} - -function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { - return tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution); -} - -const layer = new VectorTileLayer({ - declutter: true, - style: createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text), - source: new VectorTileSource({ - format: new MVT(), - url: 'https://{a-d}.tiles.mapbox.com/v4/mapbox.mapbox-streets-v6/' + - '{z}/{x}/{y}.vector.pbf?access_token=' + key - }) -}); -const renderer = layer.getRenderer(); -const tileQueue = new TileQueue(getTilePriority, function() { - worker.postMessage({action: 'request-render'}); -}); -const maxTotalLoading = 8; -const maxNewLoads = 2; - -let rendererTransform, rendererOpacity; -renderer.useContainer = function(target, transform, opacity) { - target.style = {}; - this.canvas = target; - this.context = target.getContext('2d'); - this.container = { - firstElementChild: target - }; - rendererTransform = transform; - rendererOpacity = opacity; -}; - -let rendering = false; - -worker.addEventListener('message', function(event) { - if (event.data.action !== 'render') { - return; - } - if (rendering) { - // drop this frame - worker.postMessage({action: 'request-render'}); - return; - } - frameState = event.data.frameState; - frameState.tileQueue = tileQueue; - frameState.viewState.projection.__proto__ = Projection.prototype; - rendering = true; - requestAnimationFrame(function() { - renderer.renderFrame(frameState, canvas); - renderDeclutterItems(frameState, null); - if (tileQueue.getTilesLoading() < maxTotalLoading) { - tileQueue.reprioritize(); // FIXME only call if view has changed - tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); - } - const imageData = canvas.transferToImageBitmap(); - worker.postMessage({ - action: 'rendered', - imageData: imageData, - transform: rendererTransform, - opacity: rendererOpacity, - frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) - }, [imageData]); - rendering = false; - }); -}); - -export let create; diff --git a/examples/offscreen-canvas-tiles.css b/examples/offscreen-canvas-tiles.css index 33e90f7301..9fde055492 100644 --- a/examples/offscreen-canvas-tiles.css +++ b/examples/offscreen-canvas-tiles.css @@ -1,3 +1,3 @@ .map { - background: #f8f4f0; + background: rgba(232, 230, 223, 1); } diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index 60ee70480c..29243c2d9d 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -1,11 +1,12 @@ import Map from '../src/ol/Map.js'; import View from '../src/ol/View.js'; import Layer from '../src/ol/layer/Layer.js'; -//eslint-disable-next-line -import Worker from 'worker-loader!./mvtlayer.worker.js'; +import Worker from 'worker-loader!./offscreen-canvas-tiles.worker.js'; //eslint-disable-line import {compose, create} from '../src/ol/transform.js'; import {createTransformString} from '../src/ol/render/canvas.js'; import {getFontParameters} from '../src/ol/css.js'; +import {createXYZ} from '../src/ol/tilegrid.js'; +import {FullScreen} from '../src/ol/control.js'; const mvtLayerWorker = new Worker(); @@ -14,7 +15,7 @@ mvtLayerWorker.addEventListener('message', event => { if (event.data.action === 'getFontParameters') { getFontParameters(event.data.font, font => { mvtLayerWorker.postMessage({ - action: 'getFontParameters', + action: 'gotFontParameters', font: font }); }); @@ -28,12 +29,12 @@ mvtLayerWorker.addEventListener('message', event => { mvtLayerWorker.postMessage({ action: 'imageLoaded', image: imageBitmap, - iconName: event.data.iconName + src: event.data.src }, [imageBitmap]); }); }); - image.src = 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + event.data.iconName + '-15.svg'; - loadingImages[event.data.iconName] = true; + image.src = event.data.src; + loadingImages[event.data.src] = true; } } }); @@ -112,10 +113,12 @@ const map = new Map({ ], target: 'map', view: new View({ + resolutions: createXYZ({tileSize: 512}).getResolutions89, center: [0, 0], zoom: 2 }) }); +map.addControl(new FullScreen()); mvtLayerWorker.addEventListener('message', function(message) { if (message.data.action === 'request-render') { map.render(); @@ -125,7 +128,6 @@ mvtLayerWorker.addEventListener('message', function(message) { canvas.width = imageData.width; canvas.height = imageData.height; canvas.getContext('2d').drawImage(imageData, 0, 0); - canvas.style.opacity = message.data.opacity; canvas.style.transform = message.data.transform; workerFrameState = message.data.frameState; updateContainerTransform(); diff --git a/examples/offscreen-canvas-tiles.worker.js b/examples/offscreen-canvas-tiles.worker.js new file mode 100644 index 0000000000..d801747de5 --- /dev/null +++ b/examples/offscreen-canvas-tiles.worker.js @@ -0,0 +1,154 @@ +import VectorTileLayer from '../src/ol/layer/VectorTile.js'; +import VectorTileSource from '../src/ol/source/VectorTile.js'; +import MVT from '../src/ol/format/MVT.js'; +import {Projection} from '../src/ol/proj.js'; +import TileQueue from '../src/ol/TileQueue.js'; +import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; +import {renderDeclutterItems} from '../src/ol/render.js'; +import styleFunction from 'ol-mapbox-style/dist/stylefunction.js'; +import {inView} from '../src/ol/layer/Layer.js'; + +/** @type {any} */ +const worker = self; + +let frameState, pixelRatio; +const canvas = new OffscreenCanvas(1, 1); + +function getCircularReplacer() { + const seen = new WeakSet(); + return function(key, value) { + if (typeof value === 'object' && value !== null) { + if (seen.has(value)) { + return '[circular]'; + } + seen.add(value); + } + return value; + }; +} + +function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { + return tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution); +} + +const landcover = new VectorTileLayer({ + visible: false, + declutter: true, + maxZoom: 9, + source: new VectorTileSource({ + maxZoom: 9, + format: new MVT(), + url: 'https://api.maptiler.com/tiles/landcover/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' + }) +}); +const contours = new VectorTileLayer({ + visible: false, + declutter: true, + minZoom: 9, + maxZoom: 14, + source: new VectorTileSource({ + minZoom: 9, + maxZoom: 14, + format: new MVT(), + url: 'https://api.maptiler.com/tiles/contours/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' + }) +}); +const openmaptiles = new VectorTileLayer({ + visible: false, + declutter: true, + source: new VectorTileSource({ + format: new MVT(), + maxZoom: 14, + url: 'https://api.maptiler.com/tiles/v3/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' + }) +}); + +const layers = [landcover, contours, openmaptiles]; +let rendererTransform; +layers.forEach(layer => { + layer.once('change', () => { + layer.setVisible(true); + worker.postMessage({action: 'request-render'}); + }); + layer.getRenderer().useContainer = function(target, transform) { + this.containerReused = this.getLayer() !== layers[0]; + target.style = {}; + this.canvas = target; + this.context = target.getContext('2d'); + this.container = { + firstElementChild: target + }; + rendererTransform = transform; + }; +}); + +function getFont(font) { + return font[0] + .replace('Noto Sans', 'serif') + .replace('Roboto', 'sans-serif'); +} + +function loadStyles() { + const styleUrl = 'https://api.maptiler.com/maps/topo/style.json?key=get_your_own_D6rA4zTHduk6KOKTXzGB'; + fetch(styleUrl).then(data => data.json()).then(styleJson => { + const spriteUrl = styleJson.sprite + (pixelRatio > 1 ? '@2x' : '') + '.json'; + const spriteImageUrl = styleJson.sprite + (pixelRatio > 1 ? '@2x' : '') + '.png'; + fetch(spriteUrl).then(data => data.json()).then(spriteJson => { + styleFunction(landcover, styleJson, 'landcover', undefined, spriteJson, spriteImageUrl, getFont); + styleFunction(contours, styleJson, 'contours', undefined, spriteJson, spriteImageUrl, getFont); + styleFunction(openmaptiles, styleJson, 'openmaptiles', undefined, spriteJson, spriteImageUrl, getFont); + }); + }); +} + +const tileQueue = new TileQueue(getTilePriority, () => { + worker.postMessage({action: 'request-render'}); +}); +const maxTotalLoading = 8; +const maxNewLoads = 2; + +let rendering = false; + +worker.addEventListener('message', event => { + if (event.data.action !== 'render') { + return; + } + frameState = event.data.frameState; + if (!pixelRatio) { + pixelRatio = frameState.pixelRatio; + loadStyles(); + } + frameState.tileQueue = tileQueue; + frameState.viewState.projection.__proto__ = Projection.prototype; + if (rendering) { + return; + } + rendering = true; + requestAnimationFrame(function() { + let rendered = false; + layers.forEach(layer => { + if (inView(layer.getLayerState(), frameState.viewState)) { + rendered = true; + const renderer = layer.getRenderer(); + renderer.renderFrame(frameState, canvas); + } + }); + rendering = false; + if (!rendered) { + return; + } + renderDeclutterItems(frameState, null); + if (tileQueue.getTilesLoading() < maxTotalLoading) { + tileQueue.reprioritize(); // FIXME only call if view has changed + tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); + } + const imageData = canvas.transferToImageBitmap(); + worker.postMessage({ + action: 'rendered', + imageData: imageData, + transform: rendererTransform, + frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + }, [imageData]); + }); +}); + diff --git a/examples/resources/mapbox-streets-v6-style.js b/examples/resources/mapbox-streets-v6-style.js index e1f0197bf8..afc1d8605d 100644 --- a/examples/resources/mapbox-streets-v6-style.js +++ b/examples/resources/mapbox-streets-v6-style.js @@ -2,20 +2,6 @@ // http://a.tiles.mapbox.com/v4/mapbox.mapbox-streets-v6.json function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { - - let worker; - try { - worker = self.document ? null : self; - worker.addEventListener('message', message => { - if (message.data.type === 'imageLoaded') { - iconCache[message.data.iconName].setImage(new Icon({ - img: message.data.image, - imgSize: [15, 15] - })); - } - }); - } catch (e) {} - var fill = new Fill({color: ''}); var stroke = new Stroke({color: '', width: 1}); var polygon = new Style({fill: fill}); @@ -28,19 +14,11 @@ function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { function getIcon(iconName) { var icon = iconCache[iconName]; if (!icon) { - if (!worker) { - icon = new Style({image: new Icon({ - src: 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + iconName + '-15.svg', - imgSize: [15, 15], - crossOrigin: 'anonymous' - })}); - } else { - icon = new Style({}); - worker.postMessage({ - type: 'loadImage', - iconName: iconName - }); - } + icon = new Style({image: new Icon({ + src: 'https://unpkg.com/@mapbox/maki@4.0.0/icons/' + iconName + '-15.svg', + imgSize: [15, 15], + crossOrigin: 'anonymous' + })}); iconCache[iconName] = icon; } return icon; @@ -331,8 +309,4 @@ function createMapboxStreetsV6Style(Style, Fill, Stroke, Icon, Text) { styles.length = length; return styles; }; -} - -try { - module.exports = createMapboxStreetsV6Style; -} catch (e) {} +} \ No newline at end of file From 941df3b270aee8d8679999c09afdc1d5fdaf6079 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:19:15 +0100 Subject: [PATCH 055/119] Fix issues with TypeScript's built-in webworker lib --- tsconfig.json | 1 + 1 file changed, 1 insertion(+) diff --git a/tsconfig.json b/tsconfig.json index 3a208514a3..4a838e8614 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -6,6 +6,7 @@ "lib": ["es2017", "dom", "webworker"], /* Specify library files to be included in the compilation. */ "allowJs": true, /* Allow javascript files to be compiled. */ "checkJs": true, /* Report errors in .js files. */ + "skipLibCheck": true, // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */ // "declaration": true, /* Generates corresponding '.d.ts' file. */ // "sourceMap": true, /* Generates corresponding '.map' file. */ From 828becf68e70fa3b97b95adcdf8922489db3a3a9 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 22 Mar 2020 20:49:40 +0100 Subject: [PATCH 056/119] Position rotate control in the bottom left --- examples/mapbox-style.css | 6 ++++++ examples/offscreen-canvas-tiles.css | 6 ++++++ 2 files changed, 12 insertions(+) create mode 100644 examples/mapbox-style.css diff --git a/examples/mapbox-style.css b/examples/mapbox-style.css new file mode 100644 index 0000000000..c79f84a2c1 --- /dev/null +++ b/examples/mapbox-style.css @@ -0,0 +1,6 @@ +.ol-rotate { + left: .5em; + bottom: .5em; + top: unset; + right: unset; +} \ No newline at end of file diff --git a/examples/offscreen-canvas-tiles.css b/examples/offscreen-canvas-tiles.css index 9fde055492..10bacb9a63 100644 --- a/examples/offscreen-canvas-tiles.css +++ b/examples/offscreen-canvas-tiles.css @@ -1,3 +1,9 @@ .map { background: rgba(232, 230, 223, 1); } +.ol-rotate { + left: .5em; + bottom: .5em; + top: unset; + right: unset; +} \ No newline at end of file From 0e1af6836ffbf195cb5715ad6f5edaacbfdb7584 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 23 Mar 2020 12:46:06 +0100 Subject: [PATCH 057/119] Example cleanup --- examples/offscreen-canvas-tiles.html | 1 + examples/offscreen-canvas-tiles.js | 126 +++++++++------------ examples/offscreen-canvas-tiles.worker.js | 129 ++++++++++------------ package.json | 1 + 4 files changed, 114 insertions(+), 143 deletions(-) diff --git a/examples/offscreen-canvas-tiles.html b/examples/offscreen-canvas-tiles.html index 231da2f14f..741d469e23 100644 --- a/examples/offscreen-canvas-tiles.html +++ b/examples/offscreen-canvas-tiles.html @@ -5,5 +5,6 @@ shortdesc: Example of a map that delegates rendering to a worker. docs: > The map in this example is rendered in a web worker, using `OffscreenCanvas`. **Note:** This is currently only supported in Chrome and Edge. tags: "worker, offscreencanvas, vector-tiles" +experimental: true ---
diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas-tiles.js index 29243c2d9d..53696a7414 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas-tiles.js @@ -4,56 +4,16 @@ import Layer from '../src/ol/layer/Layer.js'; import Worker from 'worker-loader!./offscreen-canvas-tiles.worker.js'; //eslint-disable-line import {compose, create} from '../src/ol/transform.js'; import {createTransformString} from '../src/ol/render/canvas.js'; -import {getFontParameters} from '../src/ol/css.js'; import {createXYZ} from '../src/ol/tilegrid.js'; import {FullScreen} from '../src/ol/control.js'; +import stringify from 'json-stringify-safe'; -const mvtLayerWorker = new Worker(); - -const loadingImages = {}; -mvtLayerWorker.addEventListener('message', event => { - if (event.data.action === 'getFontParameters') { - getFontParameters(event.data.font, font => { - mvtLayerWorker.postMessage({ - action: 'gotFontParameters', - font: font - }); - }); - } else if (event.data.action === 'loadImage') { - if (!(event.data.src in loadingImages)) { - const image = new Image(); - image.crossOrigin = 'anonymous'; - image.addEventListener('load', function() { - createImageBitmap(image, 0, 0, image.width, image.height).then(imageBitmap => { - delete loadingImages[event.data.iconName]; - mvtLayerWorker.postMessage({ - action: 'imageLoaded', - image: imageBitmap, - src: event.data.src - }, [imageBitmap]); - }); - }); - image.src = event.data.src; - loadingImages[event.data.src] = true; - } - } -}); - -function getCircularReplacer() { - const seen = new WeakSet(); - return function(key, value) { - if (typeof value === 'object' && value !== null) { - if (seen.has(value)) { - return '[circular]'; - } - seen.add(value); - } - return value; - }; -} +const worker = new Worker(); let container, transformContainer, canvas, workerFrameState, mainThreadFrameState; +// Transform the container to account for the differnece between the (newer) +// main thread frameState and the (older) worker frameState function updateContainerTransform() { if (workerFrameState) { const viewState = mainThreadFrameState.viewState; @@ -65,6 +25,8 @@ function updateContainerTransform() { const renderedResolution = renderedViewState.resolution; const renderedRotation = renderedViewState.rotation; const transform = create(); + // Skip the extra transform for rotated views, because it will not work + // correctly in that case if (!rotation) { compose(transform, (renderedCenter[0] - center[0]) / resolution, @@ -75,40 +37,36 @@ function updateContainerTransform() { } transformContainer.style.transform = createTransformString(transform); } - -} - -function render(id, frameState) { - if (!container) { - container = document.createElement('div'); - container.style.position = 'absolute'; - container.style.width = '100%'; - container.style.height = '100%'; - transformContainer = document.createElement('div'); - transformContainer.style.position = 'absolute'; - transformContainer.style.width = '100%'; - transformContainer.style.height = '100%'; - container.appendChild(transformContainer); - canvas = document.createElement('canvas'); - canvas.style.position = 'absolute'; - canvas.style.left = '0'; - canvas.style.transformOrigin = 'top left'; - transformContainer.appendChild(canvas); - } - mainThreadFrameState = frameState; - updateContainerTransform(); - mvtLayerWorker.postMessage({ - action: 'render', - id: id, - frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) - }); - return container; } const map = new Map({ layers: [ new Layer({ - render: render.bind(undefined, 'mapbox') + render: function(frameState) { + if (!container) { + container = document.createElement('div'); + container.style.position = 'absolute'; + container.style.width = '100%'; + container.style.height = '100%'; + transformContainer = document.createElement('div'); + transformContainer.style.position = 'absolute'; + transformContainer.style.width = '100%'; + transformContainer.style.height = '100%'; + container.appendChild(transformContainer); + canvas = document.createElement('canvas'); + canvas.style.position = 'absolute'; + canvas.style.left = '0'; + canvas.style.transformOrigin = 'top left'; + transformContainer.appendChild(canvas); + } + mainThreadFrameState = frameState; + updateContainerTransform(); + worker.postMessage({ + action: 'render', + frameState: JSON.parse(stringify(frameState)) + }); + return container; + } }) ], target: 'map', @@ -119,10 +77,28 @@ const map = new Map({ }) }); map.addControl(new FullScreen()); -mvtLayerWorker.addEventListener('message', function(message) { - if (message.data.action === 'request-render') { + +// Worker messaging and actions +worker.addEventListener('message', message => { + if (message.data.action === 'loadImage') { + // Image loader for ol-mapbox-style + const image = new Image(); + image.crossOrigin = 'anonymous'; + image.addEventListener('load', function() { + createImageBitmap(image, 0, 0, image.width, image.height).then(imageBitmap => { + worker.postMessage({ + action: 'imageLoaded', + image: imageBitmap, + src: event.data.src + }, [imageBitmap]); + }); + }); + image.src = event.data.src; + } else if (message.data.action === 'request-render') { + // Worker requested a new render frame map.render(); } else if (canvas && message.data.action === 'rendered') { + // Worker provies a new render frame transformContainer.style.transform = ''; const imageData = message.data.imageData; canvas.width = imageData.width; diff --git a/examples/offscreen-canvas-tiles.worker.js b/examples/offscreen-canvas-tiles.worker.js index d801747de5..e80187e7af 100644 --- a/examples/offscreen-canvas-tiles.worker.js +++ b/examples/offscreen-canvas-tiles.worker.js @@ -7,81 +7,35 @@ import {getTilePriority as tilePriorityFunction} from '../src/ol/TileQueue.js'; import {renderDeclutterItems} from '../src/ol/render.js'; import styleFunction from 'ol-mapbox-style/dist/stylefunction.js'; import {inView} from '../src/ol/layer/Layer.js'; +import stringify from 'json-stringify-safe'; /** @type {any} */ const worker = self; -let frameState, pixelRatio; +let frameState, pixelRatio, rendererTransform; const canvas = new OffscreenCanvas(1, 1); -function getCircularReplacer() { - const seen = new WeakSet(); - return function(key, value) { - if (typeof value === 'object' && value !== null) { - if (seen.has(value)) { - return '[circular]'; - } - seen.add(value); - } - return value; - }; -} - -function getTilePriority(tile, tileSourceKey, tileCenter, tileResolution) { - return tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution); -} - -const landcover = new VectorTileLayer({ - visible: false, - declutter: true, - maxZoom: 9, - source: new VectorTileSource({ +const sources = { + landcover: new VectorTileSource({ maxZoom: 9, format: new MVT(), url: 'https://api.maptiler.com/tiles/landcover/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' - }) -}); -const contours = new VectorTileLayer({ - visible: false, - declutter: true, - minZoom: 9, - maxZoom: 14, - source: new VectorTileSource({ + }), + contours: new VectorTileSource({ minZoom: 9, maxZoom: 14, format: new MVT(), url: 'https://api.maptiler.com/tiles/contours/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' - }) -}); -const openmaptiles = new VectorTileLayer({ - visible: false, - declutter: true, - source: new VectorTileSource({ + }), + openmaptiles: new VectorTileSource({ format: new MVT(), maxZoom: 14, url: 'https://api.maptiler.com/tiles/v3/{z}/{x}/{y}.pbf?key=get_your_own_D6rA4zTHduk6KOKTXzGB' }) -}); - -const layers = [landcover, contours, openmaptiles]; -let rendererTransform; -layers.forEach(layer => { - layer.once('change', () => { - layer.setVisible(true); - worker.postMessage({action: 'request-render'}); - }); - layer.getRenderer().useContainer = function(target, transform) { - this.containerReused = this.getLayer() !== layers[0]; - target.style = {}; - this.canvas = target; - this.context = target.getContext('2d'); - this.container = { - firstElementChild: target - }; - rendererTransform = transform; - }; -}); +}; +const layers = []; +// Font replacement so we do not need to load web fonts in the worker function getFont(font) { return font[0] .replace('Noto Sans', 'serif') @@ -90,23 +44,63 @@ function getFont(font) { function loadStyles() { const styleUrl = 'https://api.maptiler.com/maps/topo/style.json?key=get_your_own_D6rA4zTHduk6KOKTXzGB'; + fetch(styleUrl).then(data => data.json()).then(styleJson => { + const buckets = []; + let currentSource; + styleJson.layers.forEach(layer => { + if (!layer.source) { + return; + } + if (currentSource !== layer.source) { + currentSource = layer.source; + buckets.push({ + source: layer.source, + layers: [] + }); + } + buckets[buckets.length - 1].layers.push(layer.id); + }); + const spriteUrl = styleJson.sprite + (pixelRatio > 1 ? '@2x' : '') + '.json'; const spriteImageUrl = styleJson.sprite + (pixelRatio > 1 ? '@2x' : '') + '.png'; fetch(spriteUrl).then(data => data.json()).then(spriteJson => { - styleFunction(landcover, styleJson, 'landcover', undefined, spriteJson, spriteImageUrl, getFont); - styleFunction(contours, styleJson, 'contours', undefined, spriteJson, spriteImageUrl, getFont); - styleFunction(openmaptiles, styleJson, 'openmaptiles', undefined, spriteJson, spriteImageUrl, getFont); + buckets.forEach(bucket => { + const source = sources[bucket.source]; + if (!source) { + return; + } + const layer = new VectorTileLayer({ + declutter: true, + source, + minZoom: source.getTileGrid().getMinZoom() + }); + layer.getRenderer().useContainer = function(target, transform) { + this.containerReused = this.getLayer() !== layers[0]; + target.style = {}; + this.canvas = target; + this.context = target.getContext('2d'); + this.container = { + firstElementChild: target + }; + rendererTransform = transform; + }; + styleFunction(layer, styleJson, bucket.layers, undefined, spriteJson, spriteImageUrl, getFont); + layers.push(layer); + }); + worker.postMessage({action: 'request-render'}); }); }); } -const tileQueue = new TileQueue(getTilePriority, () => { - worker.postMessage({action: 'request-render'}); -}); +// Minimal map-like functionality for rendering + +const tileQueue = new TileQueue( + (tile, tileSourceKey, tileCenter, tileResolution) => tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution), + () => worker.postMessage({action: 'request-render'})); + const maxTotalLoading = 8; const maxNewLoads = 2; - let rendering = false; worker.addEventListener('message', event => { @@ -124,7 +118,7 @@ worker.addEventListener('message', event => { return; } rendering = true; - requestAnimationFrame(function() { + requestAnimationFrame(() => { let rendered = false; layers.forEach(layer => { if (inView(layer.getLayerState(), frameState.viewState)) { @@ -139,7 +133,7 @@ worker.addEventListener('message', event => { } renderDeclutterItems(frameState, null); if (tileQueue.getTilesLoading() < maxTotalLoading) { - tileQueue.reprioritize(); // FIXME only call if view has changed + tileQueue.reprioritize(); tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); } const imageData = canvas.transferToImageBitmap(); @@ -147,8 +141,7 @@ worker.addEventListener('message', event => { action: 'rendered', imageData: imageData, transform: rendererTransform, - frameState: JSON.parse(JSON.stringify(frameState, getCircularReplacer())) + frameState: JSON.parse(stringify(frameState)) }, [imageData]); }); }); - diff --git a/package.json b/package.json index 67d75abf99..2eca898191 100644 --- a/package.json +++ b/package.json @@ -73,6 +73,7 @@ "jquery": "3.4.1", "jsdoc": "3.6.3", "jsdoc-plugin-typescript": "^2.0.5", + "json-stringify-safe": "^5.0.1", "karma": "^4.4.1", "karma-chrome-launcher": "3.1.0", "karma-coverage-istanbul-reporter": "^2.1.1", From 5113d7070149186ac9d1615da8fbd244dd7f1647 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 23 Mar 2020 12:58:41 +0100 Subject: [PATCH 058/119] Rename example --- examples/{offscreen-canvas-tiles.css => offscreen-canvas.css} | 0 .../{offscreen-canvas-tiles.html => offscreen-canvas.html} | 0 examples/{offscreen-canvas-tiles.js => offscreen-canvas.js} | 4 ++-- ...reen-canvas-tiles.worker.js => offscreen-canvas.worker.js} | 0 4 files changed, 2 insertions(+), 2 deletions(-) rename examples/{offscreen-canvas-tiles.css => offscreen-canvas.css} (100%) rename examples/{offscreen-canvas-tiles.html => offscreen-canvas.html} (100%) rename examples/{offscreen-canvas-tiles.js => offscreen-canvas.js} (97%) rename examples/{offscreen-canvas-tiles.worker.js => offscreen-canvas.worker.js} (100%) diff --git a/examples/offscreen-canvas-tiles.css b/examples/offscreen-canvas.css similarity index 100% rename from examples/offscreen-canvas-tiles.css rename to examples/offscreen-canvas.css diff --git a/examples/offscreen-canvas-tiles.html b/examples/offscreen-canvas.html similarity index 100% rename from examples/offscreen-canvas-tiles.html rename to examples/offscreen-canvas.html diff --git a/examples/offscreen-canvas-tiles.js b/examples/offscreen-canvas.js similarity index 97% rename from examples/offscreen-canvas-tiles.js rename to examples/offscreen-canvas.js index 53696a7414..b51fceeea2 100644 --- a/examples/offscreen-canvas-tiles.js +++ b/examples/offscreen-canvas.js @@ -1,7 +1,7 @@ import Map from '../src/ol/Map.js'; import View from '../src/ol/View.js'; import Layer from '../src/ol/layer/Layer.js'; -import Worker from 'worker-loader!./offscreen-canvas-tiles.worker.js'; //eslint-disable-line +import Worker from 'worker-loader!./offscreen-canvas.worker.js'; //eslint-disable-line import {compose, create} from '../src/ol/transform.js'; import {createTransformString} from '../src/ol/render/canvas.js'; import {createXYZ} from '../src/ol/tilegrid.js'; @@ -89,7 +89,7 @@ worker.addEventListener('message', message => { worker.postMessage({ action: 'imageLoaded', image: imageBitmap, - src: event.data.src + src: message.data.src }, [imageBitmap]); }); }); diff --git a/examples/offscreen-canvas-tiles.worker.js b/examples/offscreen-canvas.worker.js similarity index 100% rename from examples/offscreen-canvas-tiles.worker.js rename to examples/offscreen-canvas.worker.js From 576f50331bff757132f12affd2fde139e2ccbe09 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 23 Mar 2020 19:44:31 +0100 Subject: [PATCH 059/119] Add attribution --- examples/offscreen-canvas.js | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/examples/offscreen-canvas.js b/examples/offscreen-canvas.js index b51fceeea2..991b757300 100644 --- a/examples/offscreen-canvas.js +++ b/examples/offscreen-canvas.js @@ -7,6 +7,7 @@ import {createTransformString} from '../src/ol/render/canvas.js'; import {createXYZ} from '../src/ol/tilegrid.js'; import {FullScreen} from '../src/ol/control.js'; import stringify from 'json-stringify-safe'; +import Source from '../src/ol/source/Source.js'; const worker = new Worker(); @@ -66,7 +67,13 @@ const map = new Map({ frameState: JSON.parse(stringify(frameState)) }); return container; - } + }, + source: new Source({ + attributions: [ + '© MapTiler', + '© OpenStreetMap contributors' + ] + }) }) ], target: 'map', From d70b3aa3d5cc4d8e85f4f07990d42556fc641ac1 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Tue, 24 Mar 2020 10:32:37 +0100 Subject: [PATCH 060/119] Move catch-up logic to main thread This avoids requestAnimationFrame in the worker. --- examples/offscreen-canvas.js | 35 ++++++++++------- examples/offscreen-canvas.worker.js | 59 ++++++++++++----------------- 2 files changed, 45 insertions(+), 49 deletions(-) diff --git a/examples/offscreen-canvas.js b/examples/offscreen-canvas.js index 991b757300..180e5c990e 100644 --- a/examples/offscreen-canvas.js +++ b/examples/offscreen-canvas.js @@ -11,7 +11,7 @@ import Source from '../src/ol/source/Source.js'; const worker = new Worker(); -let container, transformContainer, canvas, workerFrameState, mainThreadFrameState; +let container, transformContainer, canvas, rendering, workerFrameState, mainThreadFrameState; // Transform the container to account for the differnece between the (newer) // main thread frameState and the (older) worker frameState @@ -62,10 +62,15 @@ const map = new Map({ } mainThreadFrameState = frameState; updateContainerTransform(); - worker.postMessage({ - action: 'render', - frameState: JSON.parse(stringify(frameState)) - }); + if (!rendering) { + rendering = true; + worker.postMessage({ + action: 'render', + frameState: JSON.parse(stringify(frameState)) + }); + } else { + frameState.animate = true; + } return container; }, source: new Source({ @@ -101,18 +106,20 @@ worker.addEventListener('message', message => { }); }); image.src = event.data.src; - } else if (message.data.action === 'request-render') { + } else if (message.data.action === 'requestRender') { // Worker requested a new render frame map.render(); } else if (canvas && message.data.action === 'rendered') { // Worker provies a new render frame - transformContainer.style.transform = ''; - const imageData = message.data.imageData; - canvas.width = imageData.width; - canvas.height = imageData.height; - canvas.getContext('2d').drawImage(imageData, 0, 0); - canvas.style.transform = message.data.transform; - workerFrameState = message.data.frameState; - updateContainerTransform(); + requestAnimationFrame(function() { + const imageData = message.data.imageData; + canvas.width = imageData.width; + canvas.height = imageData.height; + canvas.getContext('2d').drawImage(imageData, 0, 0); + canvas.style.transform = message.data.transform; + workerFrameState = message.data.frameState; + updateContainerTransform(); + }); + rendering = false; } }); diff --git a/examples/offscreen-canvas.worker.js b/examples/offscreen-canvas.worker.js index e80187e7af..b03f0be61d 100644 --- a/examples/offscreen-canvas.worker.js +++ b/examples/offscreen-canvas.worker.js @@ -14,6 +14,9 @@ const worker = self; let frameState, pixelRatio, rendererTransform; const canvas = new OffscreenCanvas(1, 1); +// OffscreenCanvas does not have a style, so we mock it +canvas.style = {}; +const context = canvas.getContext('2d'); const sources = { landcover: new VectorTileSource({ @@ -77,18 +80,17 @@ function loadStyles() { }); layer.getRenderer().useContainer = function(target, transform) { this.containerReused = this.getLayer() !== layers[0]; - target.style = {}; - this.canvas = target; - this.context = target.getContext('2d'); + this.canvas = canvas; + this.context = context; this.container = { - firstElementChild: target + firstElementChild: canvas }; rendererTransform = transform; }; styleFunction(layer, styleJson, bucket.layers, undefined, spriteJson, spriteImageUrl, getFont); layers.push(layer); }); - worker.postMessage({action: 'request-render'}); + worker.postMessage({action: 'requestRender'}); }); }); } @@ -97,11 +99,10 @@ function loadStyles() { const tileQueue = new TileQueue( (tile, tileSourceKey, tileCenter, tileResolution) => tilePriorityFunction(frameState, tile, tileSourceKey, tileCenter, tileResolution), - () => worker.postMessage({action: 'request-render'})); + () => worker.postMessage({action: 'requestRender'})); const maxTotalLoading = 8; const maxNewLoads = 2; -let rendering = false; worker.addEventListener('message', event => { if (event.data.action !== 'render') { @@ -114,34 +115,22 @@ worker.addEventListener('message', event => { } frameState.tileQueue = tileQueue; frameState.viewState.projection.__proto__ = Projection.prototype; - if (rendering) { - return; - } - rendering = true; - requestAnimationFrame(() => { - let rendered = false; - layers.forEach(layer => { - if (inView(layer.getLayerState(), frameState.viewState)) { - rendered = true; - const renderer = layer.getRenderer(); - renderer.renderFrame(frameState, canvas); - } - }); - rendering = false; - if (!rendered) { - return; + layers.forEach(layer => { + if (inView(layer.getLayerState(), frameState.viewState)) { + const renderer = layer.getRenderer(); + renderer.renderFrame(frameState, canvas); } - renderDeclutterItems(frameState, null); - if (tileQueue.getTilesLoading() < maxTotalLoading) { - tileQueue.reprioritize(); - tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); - } - const imageData = canvas.transferToImageBitmap(); - worker.postMessage({ - action: 'rendered', - imageData: imageData, - transform: rendererTransform, - frameState: JSON.parse(stringify(frameState)) - }, [imageData]); }); + renderDeclutterItems(frameState, null); + if (tileQueue.getTilesLoading() < maxTotalLoading) { + tileQueue.reprioritize(); + tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); + } + const imageData = canvas.transferToImageBitmap(); + worker.postMessage({ + action: 'rendered', + imageData: imageData, + transform: rendererTransform, + frameState: JSON.parse(stringify(frameState)) + }, [imageData]); }); From c3d9ac6265f7bb4816beb52a50e5d83fedd21567 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Wed, 25 Mar 2020 12:55:57 +0000 Subject: [PATCH 061/119] Fix description --- examples/earthquake-custom-symbol.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/earthquake-custom-symbol.html b/examples/earthquake-custom-symbol.html index 729d8eb3e7..34dd810d67 100644 --- a/examples/earthquake-custom-symbol.html +++ b/examples/earthquake-custom-symbol.html @@ -1,7 +1,7 @@ --- layout: example.html title: Earthquakes with custom symbols -shortdesc: Demonstrates the use of `toCanvas` to create custom icon symbols. +shortdesc: Demonstrates the use of `toContext` to create custom icon symbols. docs: > This example parses a KML file and renders the features as a vector layer. The layer is given a style that renders earthquake locations with a custom lightning symbol and a size relative to their magnitude. tags: "KML, vector, style, canvas, symbol" From 98e8bec3709364b5fd14dd71a4e4e72dcf4ae1c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mateusz=20=C5=81oskot?= Date: Mon, 21 Jan 2019 15:21:39 +0100 Subject: [PATCH 062/119] Calculate tile grid extent from extent of bottom-level tile matrix Prefers extent derived from the tile matrix set in the capabilities over default projection extent. --- src/ol/source/WMTS.js | 38 ++++++++++---------- test/spec/ol/format/wmts/ogcsample.xml | 28 ++++++++++++++- test/spec/ol/format/wmtscapabilities.test.js | 4 ++- test/spec/ol/source/wmts.test.js | 27 ++++++++++++++ 4 files changed, 77 insertions(+), 20 deletions(-) diff --git a/src/ol/source/WMTS.js b/src/ol/source/WMTS.js index c8b11c9c32..77663ad2a3 100644 --- a/src/ol/source/WMTS.js +++ b/src/ol/source/WMTS.js @@ -4,9 +4,8 @@ import {expandUrl, createFromTileUrlFunctions, nullTileUrlFunction} from '../tileurlfunction.js'; import {find, findIndex, includes} from '../array.js'; -import {containsExtent} from '../extent.js'; import {assign} from '../obj.js'; -import {get as getProjection, equivalent, transformExtent} from '../proj.js'; +import {get as getProjection, equivalent} from '../proj.js'; import TileImage from './TileImage.js'; import WMTSRequestEncoding from './WMTSRequestEncoding.js'; import {createFromCapabilitiesMatrixSet} from '../tilegrid/WMTS.js'; @@ -377,22 +376,25 @@ export function optionsFromCapabilities(wmtsCap, config) { } } - const wgs84BoundingBox = l['WGS84BoundingBox']; - let extent, wrapX; - if (wgs84BoundingBox !== undefined) { - const wgs84ProjectionExtent = getProjection('EPSG:4326').getExtent(); - wrapX = (wgs84BoundingBox[0] == wgs84ProjectionExtent[0] && - wgs84BoundingBox[2] == wgs84ProjectionExtent[2]); - extent = transformExtent( - wgs84BoundingBox, 'EPSG:4326', projection); - const projectionExtent = projection.getExtent(); - if (projectionExtent) { - // If possible, do a sanity check on the extent - it should never be - // bigger than the validity extent of the projection of a matrix set. - if (!containsExtent(projectionExtent, extent)) { - extent = undefined; - } - } + const wrapX = false; + + const matrix0 = matrixSetObj.TileMatrix[0]; + const resolution = matrix0.ScaleDenominator * 0.00028; // WMTS 1.0.0: standardized rendering pixel size + const origin = projection === getProjection('EPSG:4326') + ? [matrix0.TopLeftCorner[1], matrix0.TopLeftCorner[0]] + : matrix0.TopLeftCorner; + const tileSpanX = matrix0.TileWidth * resolution; + const tileSpanY = matrix0.TileHeight * resolution; + + const extent = [ + origin[0], + origin[1] - tileSpanY * matrix0.MatrixHeight, + origin[0] + tileSpanX * matrix0.MatrixWidth, + origin[1] + ]; + + if (projection.getExtent() === null) { + projection.setExtent(extent); } const tileGrid = createFromCapabilitiesMatrixSet(matrixSetObj, extent, matrixLimits); diff --git a/test/spec/ol/format/wmts/ogcsample.xml b/test/spec/ol/format/wmts/ogcsample.xml index fbf7b282b8..7eb006bf2b 100644 --- a/test/spec/ol/format/wmts/ogcsample.xml +++ b/test/spec/ol/format/wmts/ogcsample.xml @@ -92,6 +92,9 @@ access interface to some TileMatrixSets google3857 + + google3857subset + @@ -372,6 +375,29 @@ access interface to some TileMatrixSets 7000 - + + + google3857subset + urn:ogc:def:crs:EPSG:6.18:3:3857 + + 18 + 2132.72958385 + -10000000 10000000 + 256 + 256 + 1 + 1 + + + 18 + 1066.36479193 + -10000000 10000000 + 256 + 256 + 2 + 2 + + + diff --git a/test/spec/ol/format/wmtscapabilities.test.js b/test/spec/ol/format/wmtscapabilities.test.js index 72b907cb3f..5bcf881758 100644 --- a/test/spec/ol/format/wmtscapabilities.test.js +++ b/test/spec/ol/format/wmtscapabilities.test.js @@ -54,11 +54,13 @@ describe('ol.format.WMTSCapabilities', function() { expect(layer.Style[0].LegendURL[0].format).to.be.eql('image/png'); expect(layer.TileMatrixSetLink).to.be.an('array'); - expect(layer.TileMatrixSetLink).to.have.length(2); + expect(layer.TileMatrixSetLink).to.have.length(3); expect(layer.TileMatrixSetLink[0].TileMatrixSet).to.be .eql('BigWorldPixel'); expect(layer.TileMatrixSetLink[1].TileMatrixSet).to.be .eql('google3857'); + expect(layer.TileMatrixSetLink[2].TileMatrixSet).to.be + .eql('google3857subset'); const wgs84Bbox = layer.WGS84BoundingBox; expect(wgs84Bbox).to.be.an('array'); diff --git a/test/spec/ol/source/wmts.test.js b/test/spec/ol/source/wmts.test.js index b49d71e787..20cf5a41e1 100644 --- a/test/spec/ol/source/wmts.test.js +++ b/test/spec/ol/source/wmts.test.js @@ -1,4 +1,5 @@ import WMTSCapabilities from '../../../../src/ol/format/WMTSCapabilities.js'; +import {getBottomLeft, getTopRight} from '../../../../src/ol/extent.js'; import {get as getProjection} from '../../../../src/ol/proj.js'; import Projection from '../../../../src/ol/proj/Projection.js'; import WMTSTileGrid from '../../../../src/ol/tilegrid/WMTS.js'; @@ -149,6 +150,32 @@ describe('ol.source.WMTS', function() { expect(options.projection.getCode()).to.be.eql('urn:ogc:def:crs:OGC:1.3:CRS84'); }); + it('uses extent of tile matrix instead of projection extent', function() { + const options = optionsFromCapabilities(capabilities, + {layer: 'BlueMarbleNextGeneration', matrixSet: 'google3857subset'}); + + // Since google3857subset defines subset of space defined by the google3857 matrix set: + // - top left corner: -10000000, 10000000 + // - calculated grid extent: [-10000000, 9999694.25188686, -9999694.25188686, 10000000] + // then the tile grid extent is only a part of the full projection extent. + + const gridExtent = options.tileGrid.getExtent(); + const gridBottomLeft = getBottomLeft(gridExtent); + const gridTopRight = getTopRight(gridExtent); + expect(Math.round(gridBottomLeft[0])).to.be.eql(-10000000); + expect(Math.round(gridBottomLeft[1])).to.be.eql(9999847); + expect(Math.round(gridTopRight[0])).to.be.eql(-9999847); + expect(Math.round(gridTopRight[1])).to.be.eql(10000000); + + const projExtent = options.projection.getExtent(); + const projBottomLeft = getBottomLeft(projExtent); + const projTopRight = getTopRight(projExtent); + expect(Math.round(projBottomLeft[0])).to.be.eql(-20037508); + expect(Math.round(projBottomLeft[1])).to.be.eql(-20037508); + expect(Math.round(projTopRight[0])).to.be.eql(20037508); + expect(Math.round(projTopRight[1])).to.be.eql(20037508); + }); + it('doesn\'t fail if the GetCap doesn\'t contains Constraint tags', function() { const tmpXml = content.replace(//g, ''); const tmpCapabilities = parser.read(tmpXml); From fbe7b0bd78dc4c4a59b72219d6e5fce6cf6a21a0 Mon Sep 17 00:00:00 2001 From: Szabo Bogdan Date: Thu, 26 Mar 2020 19:00:13 +0100 Subject: [PATCH 063/119] Fix test typo --- test/spec/ol/layer/vector.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/spec/ol/layer/vector.test.js b/test/spec/ol/layer/vector.test.js index e53523166c..65c6f2a163 100644 --- a/test/spec/ol/layer/vector.test.js +++ b/test/spec/ol/layer/vector.test.js @@ -141,7 +141,7 @@ describe('ol.layer.Vector', function() { }), new Feature({ geometry: new Point([1000000, 0]), - name: 'feture2' + name: 'feature2' }) ] }) From 6aa398cbecbe63d2b5bc3475ad9bdb62e99bee91 Mon Sep 17 00:00:00 2001 From: Szabo Bogdan Date: Thu, 26 Mar 2020 21:18:57 +0100 Subject: [PATCH 064/119] Fix hit detection for images with missing size --- src/ol/render/canvas/hitdetect.js | 4 +++ test/spec/ol/layer/vector.test.js | 48 +++++++++++++++++++++++-------- 2 files changed, 40 insertions(+), 12 deletions(-) diff --git a/src/ol/render/canvas/hitdetect.js b/src/ol/render/canvas/hitdetect.js index ef21f3d9e9..ced9974156 100644 --- a/src/ol/render/canvas/hitdetect.js +++ b/src/ol/render/canvas/hitdetect.js @@ -65,6 +65,10 @@ export function createHitDetectionImageData(size, transforms, features, styleFun const image = originalStyle.getImage(); if (image) { const imgSize = image.getImageSize(); + if (!imgSize) { + continue; + } + const canvas = document.createElement('canvas'); canvas.width = imgSize[0]; canvas.height = imgSize[1]; diff --git a/test/spec/ol/layer/vector.test.js b/test/spec/ol/layer/vector.test.js index 65c6f2a163..21e8ae4534 100644 --- a/test/spec/ol/layer/vector.test.js +++ b/test/spec/ol/layer/vector.test.js @@ -6,6 +6,7 @@ import Feature from '../../../../src/ol/Feature.js'; import Point from '../../../../src/ol/geom/Point.js'; import Map from '../../../../src/ol/Map.js'; import View from '../../../../src/ol/View.js'; +import ImageStyle from '../../../../src/ol/style/Image.js'; describe('ol.layer.Vector', function() { @@ -132,19 +133,41 @@ describe('ol.layer.Vector', function() { let map, layer; beforeEach(function() { + const source = new VectorSource({ + features: [ + new Feature({ + geometry: new Point([-1000000, 0]), + name: 'feature1' + }), + new Feature({ + geometry: new Point([1000000, 0]), + name: 'feature2' + }) + ] + }); + + const feature = new Feature({ + geometry: new Point([-1000000, 0]), + name: 'feature with no size' + }); + + const testImage = new ImageStyle({ + opacity: 1, + displacement: [] + }); + + testImage.getImageState = () => {}; + testImage.listenImageChange = () => {}; + testImage.getImageSize = () => {}; + + feature.setStyle([new Style({ + image: testImage + })]); + + source.addFeature(feature); + layer = new VectorLayer({ - source: new VectorSource({ - features: [ - new Feature({ - geometry: new Point([-1000000, 0]), - name: 'feature1' - }), - new Feature({ - geometry: new Point([1000000, 0]), - name: 'feature2' - }) - ] - }) + source }); const container = document.createElement('div'); container.style.width = '256px'; @@ -171,6 +194,7 @@ describe('ol.layer.Vector', function() { map.renderSync(); const pixel = map.getPixelFromCoordinate([-1000000, 0]); layer.getFeatures(pixel).then(function(features) { + expect(features.length).to.equal(1); expect(features[0].get('name')).to.be('feature1'); done(); }); From 83a5cd63c67beed1cc8b8c63ea082a33cd75dc32 Mon Sep 17 00:00:00 2001 From: horsenit Date: Fri, 27 Mar 2020 00:32:10 -0400 Subject: [PATCH 065/119] Speed up Overlay element positioning using CSS translate() --- src/ol/Overlay.js | 80 +++++++++++++---------------------------------- 1 file changed, 22 insertions(+), 58 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index fa71db0591..f1eab6c17f 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -158,17 +158,11 @@ class Overlay extends BaseObject { /** * @protected - * @type {{bottom_: string, - * left_: string, - * right_: string, - * top_: string, + * @type {{transform_: string, * visible: boolean}} */ this.rendered = { - bottom_: '', - left_: '', - right_: '', - top_: '', + transform_: '', visible: true }; @@ -506,63 +500,33 @@ class Overlay extends BaseObject { this.setVisible(true); - let offsetX = offset[0]; - let offsetY = offset[1]; + const x = Math.round(pixel[0] + offset[0]) + 'px'; + const y = Math.round(pixel[1] + offset[1]) + 'px'; + let posX = '0%'; + let posY = '0%'; if (positioning == OverlayPositioning.BOTTOM_RIGHT || positioning == OverlayPositioning.CENTER_RIGHT || positioning == OverlayPositioning.TOP_RIGHT) { - if (this.rendered.left_ !== '') { - this.rendered.left_ = ''; - style.left = ''; - } - const right = Math.round(mapSize[0] - pixel[0] - offsetX) + 'px'; - if (this.rendered.right_ != right) { - this.rendered.right_ = right; - style.right = right; - } - } else { - if (this.rendered.right_ !== '') { - this.rendered.right_ = ''; - style.right = ''; - } - if (positioning == OverlayPositioning.BOTTOM_CENTER || - positioning == OverlayPositioning.CENTER_CENTER || - positioning == OverlayPositioning.TOP_CENTER) { - offsetX -= this.element.offsetWidth / 2; - } - const left = Math.round(pixel[0] + offsetX) + 'px'; - if (this.rendered.left_ != left) { - this.rendered.left_ = left; - style.left = left; - } + posX = '-100%'; + } else if (positioning == OverlayPositioning.BOTTOM_CENTER || + positioning == OverlayPositioning.CENTER_CENTER || + positioning == OverlayPositioning.TOP_CENTER) { + posX = '-50%'; } if (positioning == OverlayPositioning.BOTTOM_LEFT || positioning == OverlayPositioning.BOTTOM_CENTER || positioning == OverlayPositioning.BOTTOM_RIGHT) { - if (this.rendered.top_ !== '') { - this.rendered.top_ = ''; - style.top = ''; - } - const bottom = Math.round(mapSize[1] - pixel[1] - offsetY) + 'px'; - if (this.rendered.bottom_ != bottom) { - this.rendered.bottom_ = bottom; - style.bottom = bottom; - } - } else { - if (this.rendered.bottom_ !== '') { - this.rendered.bottom_ = ''; - style.bottom = ''; - } - if (positioning == OverlayPositioning.CENTER_LEFT || - positioning == OverlayPositioning.CENTER_CENTER || - positioning == OverlayPositioning.CENTER_RIGHT) { - offsetY -= this.element.offsetHeight / 2; - } - const top = Math.round(pixel[1] + offsetY) + 'px'; - if (this.rendered.top_ != top) { - this.rendered.top_ = 'top'; - style.top = top; - } + posY = '-100%'; + } else if (positioning == OverlayPositioning.CENTER_LEFT || + positioning == OverlayPositioning.CENTER_CENTER || + positioning == OverlayPositioning.CENTER_RIGHT) { + posY = '-50%'; + } + const transform = `translate(${posX}, ${posY}) translate(${x}, ${y})`; + if (this.rendered.transform_ != transform) { + this.rendered.transform_ = transform; + style.transform = transform; + style.msTransform = transform; // IE9 } } From 03ea8911f6253e63bf8bf68757b454436e223b58 Mon Sep 17 00:00:00 2001 From: horsenit Date: Fri, 27 Mar 2020 03:03:21 -0400 Subject: [PATCH 066/119] Fix type checking for IE9 style.msTransform --- src/ol/Overlay.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index f1eab6c17f..3a91f63394 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -526,7 +526,8 @@ class Overlay extends BaseObject { if (this.rendered.transform_ != transform) { this.rendered.transform_ = transform; style.transform = transform; - style.msTransform = transform; // IE9 + // @ts-ignore IE9 + style.msTransform = transform; } } From 1020c384bbb601af764402a40b294fc6ccf46dd2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maximilian=20Kr=C3=B6g?= Date: Sat, 11 Jan 2020 23:46:52 +0100 Subject: [PATCH 067/119] Fix two missing apidoc links Add IconAnchorUnits and IconOrigin to the api. --- src/ol/style/IconAnchorUnits.js | 7 +++++++ src/ol/style/IconOrigin.js | 13 +++++++++++++ 2 files changed, 20 insertions(+) diff --git a/src/ol/style/IconAnchorUnits.js b/src/ol/style/IconAnchorUnits.js index eaa549d3ce..95d9562bc2 100644 --- a/src/ol/style/IconAnchorUnits.js +++ b/src/ol/style/IconAnchorUnits.js @@ -5,8 +5,15 @@ /** * Icon anchor units. One of 'fraction', 'pixels'. * @enum {string} + * @api */ export default { + /** + * Anchor is a fraction + */ FRACTION: 'fraction', + /** + * Anchor is in pixels + */ PIXELS: 'pixels' }; diff --git a/src/ol/style/IconOrigin.js b/src/ol/style/IconOrigin.js index d1bad0bdf7..f756a5df2d 100644 --- a/src/ol/style/IconOrigin.js +++ b/src/ol/style/IconOrigin.js @@ -5,10 +5,23 @@ /** * Icon origin. One of 'bottom-left', 'bottom-right', 'top-left', 'top-right'. * @enum {string} + * @api */ export default { + /** + * Origin is at bottom left + */ BOTTOM_LEFT: 'bottom-left', + /** + * Origin is at bottom right + */ BOTTOM_RIGHT: 'bottom-right', + /** + * Origin is at top left + */ TOP_LEFT: 'top-left', + /** + * Origin is at top right + */ TOP_RIGHT: 'top-right' }; From a6a5b72c57d3a9cceaad2ab4dde45df177a861bb Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Fri, 27 Mar 2020 12:24:41 +0100 Subject: [PATCH 068/119] Only mark items as api, not enums --- src/ol/style/IconAnchorUnits.js | 3 ++- src/ol/style/IconOrigin.js | 5 ++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/src/ol/style/IconAnchorUnits.js b/src/ol/style/IconAnchorUnits.js index 95d9562bc2..af81e71ff2 100644 --- a/src/ol/style/IconAnchorUnits.js +++ b/src/ol/style/IconAnchorUnits.js @@ -5,15 +5,16 @@ /** * Icon anchor units. One of 'fraction', 'pixels'. * @enum {string} - * @api */ export default { /** * Anchor is a fraction + * @api */ FRACTION: 'fraction', /** * Anchor is in pixels + * @api */ PIXELS: 'pixels' }; diff --git a/src/ol/style/IconOrigin.js b/src/ol/style/IconOrigin.js index f756a5df2d..7ef62e96c8 100644 --- a/src/ol/style/IconOrigin.js +++ b/src/ol/style/IconOrigin.js @@ -5,23 +5,26 @@ /** * Icon origin. One of 'bottom-left', 'bottom-right', 'top-left', 'top-right'. * @enum {string} - * @api */ export default { /** * Origin is at bottom left + * @api */ BOTTOM_LEFT: 'bottom-left', /** * Origin is at bottom right + * @api */ BOTTOM_RIGHT: 'bottom-right', /** * Origin is at top left + * @api */ TOP_LEFT: 'top-left', /** * Origin is at top right + * @api */ TOP_RIGHT: 'top-right' }; From dd44ecf18516425516dbd58756a2c55a0f06c521 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sat, 28 Mar 2020 10:51:25 +0100 Subject: [PATCH 069/119] Only document enums when they have API properties --- config/jsdoc/api/plugins/api.js | 12 +++++------- config/jsdoc/api/template/tmpl/method.tmpl | 11 ++++------- 2 files changed, 9 insertions(+), 14 deletions(-) diff --git a/config/jsdoc/api/plugins/api.js b/config/jsdoc/api/plugins/api.js index c384d86dad..53e0a8c174 100644 --- a/config/jsdoc/api/plugins/api.js +++ b/config/jsdoc/api/plugins/api.js @@ -73,9 +73,6 @@ function includeAugments(doclet) { }); } cls._hideConstructor = true; - if (!cls.undocumented) { - cls._documented = true; - } } } } @@ -182,13 +179,14 @@ exports.handlers = { doclet._hideConstructor = true; includeAugments(doclet); sortOtherMembers(doclet); - } else if (!doclet._hideConstructor - && !(doclet.longname in defaultExports && byLongname[doclet.longname].some(d => d.isEnum))) { + } else if (!doclet._hideConstructor) { // Remove all other undocumented symbols doclet.undocumented = true; } - if (doclet._documented) { - delete doclet.undocumented; + if (doclet.memberof && byLongname[doclet.memberof] && + byLongname[doclet.memberof][0].isEnum && + !byLongname[doclet.memberof][0].properties.some(p => p.stability)) { + byLongname[doclet.memberof][0].undocumented = true; } } }, diff --git a/config/jsdoc/api/template/tmpl/method.tmpl b/config/jsdoc/api/template/tmpl/method.tmpl index a5ddc77f5d..9ff68aa638 100644 --- a/config/jsdoc/api/template/tmpl/method.tmpl +++ b/config/jsdoc/api/template/tmpl/method.tmpl @@ -64,7 +64,7 @@ var self = this;
  • - - - () - + + + () - From b1b01cf94386817405482f3aa7f6a9fdc986bc7d Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Mon, 30 Mar 2020 07:12:52 +0200 Subject: [PATCH 070/119] Allow pan options supplied as autoPan * Follow the suggestion from @ahocevar to use the existing autoPan constructor option instead of creating a new autoPanOptions option * Internally also store the autoPanOptions in autoPan --- src/ol/Overlay.js | 36 +++++++++++++++++++----------------- 1 file changed, 19 insertions(+), 17 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index 941aadda3d..dff3e1fe25 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -37,16 +37,18 @@ import {containsExtent} from './extent.js'; * container as that of the controls (see the `stopEvent` option) you will * probably set `insertFirst` to `true` so the overlay is displayed below the * controls. - * @property {boolean} [autoPan=false] If set to `true` the map is panned when - * calling `setPosition`, so that the overlay is entirely visible in the current - * viewport. + * @property {PanIntoViewOptions|boolean} [autoPan=false] Pan the map when calling + * `setPosition`, so that the overlay is entirely visible in the current viewport? + * If `true` (deprecated), then `autoPanAnimation` and `autoPanMargin` will be + * used to determine the panning parameters; if an object is supplied then other + * parameters are ignored. * @property {PanOptions} [autoPanAnimation] The animation options used to pan * the overlay into view. This animation is only used when `autoPan` is enabled. * A `duration` and `easing` may be provided to customize the animation. - * Deprecated and ignored if `autoPanOptions` is supplied. + * Deprecated and ignored if `autoPan` is supplied as an object. * @property {number} [autoPanMargin=20] The margin (in pixels) between the * overlay and the borders of the map when autopanning. Deprecated and ignored - * if `autoPanOptions` is supplied. + * if `autoPan` is supplied as an object. * @property {PanIntoViewOptions} [autoPanOptions] The options to use for the * autoPan. This is only used when `autoPan` is enabled and has preference over * the individual `autoPanMargin` and `autoPanOptions`. @@ -147,20 +149,18 @@ class Overlay extends BaseObject { options.className : 'ol-overlay-container ' + CLASS_SELECTABLE; this.element.style.position = 'absolute'; + let autoPan = options.autoPan; + if (autoPan && ('object' !== typeof autoPan)) { + autoPan = { + animation: options.autoPanAnimation, + margin: options.autoPanMargin + }; + } /** * @protected - * @type {boolean} + * @type {PanIntoViewOptions|false} */ - this.autoPan = options.autoPan !== undefined ? options.autoPan : false; - - /** - * @protected - * @type {PanIntoViewOptions} - */ - this.autoPanOptions = options.autoPanOptions || { - animation: options.autoPanAnimation, - margin: options.autoPanMargin - }; + this.autoPan = /** @type {PanIntoViewOptions} */(autoPan) || false; /** * @protected @@ -389,7 +389,9 @@ class Overlay extends BaseObject { * @protected */ performAutoPan() { - this.panIntoView(this.autoPanOptions); + if (this.autoPan) { + this.panIntoView(this.autoPan); + } } /** From 2537da690af03614788afcf80c681de7c6183b0d Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Mon, 30 Mar 2020 07:15:03 +0200 Subject: [PATCH 071/119] Add check that Position is set in panIntoView() * If panIntoView is an API method, it may now be called when the position of the overlay has not yet been set. * Adds a check for a set position to the panIntoView() method, and removes the now unneccessary check in handlePositionChanged() --- src/ol/Overlay.js | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index dff3e1fe25..7b82dfe5f4 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -328,9 +328,7 @@ class Overlay extends BaseObject { */ handlePositionChanged() { this.updatePixelPosition(); - if (this.get(Property.POSITION) && this.autoPan) { - this.performAutoPan(); - } + this.performAutoPan(); } /** @@ -403,7 +401,7 @@ class Overlay extends BaseObject { panIntoView(panIntoViewOptions) { const map = this.getMap(); - if (!map || !map.getTargetElement()) { + if (!map || !map.getTargetElement() || !this.get(Property.POSITION)) { return; } From 8222118fb181bf4ebc01ca6469a212e8edfd69ab Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 30 Mar 2020 08:55:08 +0000 Subject: [PATCH 072/119] Bump webpack from 4.42.0 to 4.42.1 Bumps [webpack](https://github.com/webpack/webpack) from 4.42.0 to 4.42.1. - [Release notes](https://github.com/webpack/webpack/releases) - [Commits](https://github.com/webpack/webpack/compare/v4.42.0...v4.42.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 232 ++++++++++++++++++++++++---------------------- package.json | 2 +- 2 files changed, 121 insertions(+), 113 deletions(-) diff --git a/package-lock.json b/package-lock.json index 450a9667f9..046b8b0fd2 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1808,178 +1808,177 @@ } }, "@webassemblyjs/ast": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.8.5.tgz", - "integrity": "sha512-aJMfngIZ65+t71C3y2nBBg5FFG0Okt9m0XEgWZ7Ywgn1oMAT8cNwx00Uv1cQyHtidq0Xn94R4TAywO+LCQ+ZAQ==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.9.0.tgz", + "integrity": "sha512-C6wW5L+b7ogSDVqymbkkvuW9kruN//YisMED04xzeBBqjHa2FYnmvOlS6Xj68xWQRgWvI9cIglsjFowH/RJyEA==", "dev": true, "requires": { - "@webassemblyjs/helper-module-context": "1.8.5", - "@webassemblyjs/helper-wasm-bytecode": "1.8.5", - "@webassemblyjs/wast-parser": "1.8.5" + "@webassemblyjs/helper-module-context": "1.9.0", + "@webassemblyjs/helper-wasm-bytecode": "1.9.0", + "@webassemblyjs/wast-parser": "1.9.0" } }, "@webassemblyjs/floating-point-hex-parser": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.8.5.tgz", - "integrity": "sha512-9p+79WHru1oqBh9ewP9zW95E3XAo+90oth7S5Re3eQnECGq59ly1Ri5tsIipKGpiStHsUYmY3zMLqtk3gTcOtQ==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.9.0.tgz", + "integrity": "sha512-TG5qcFsS8QB4g4MhrxK5TqfdNe7Ey/7YL/xN+36rRjl/BlGE/NcBvJcqsRgCP6Z92mRE+7N50pRIi8SmKUbcQA==", "dev": true }, "@webassemblyjs/helper-api-error": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.8.5.tgz", - "integrity": "sha512-Za/tnzsvnqdaSPOUXHyKJ2XI7PDX64kWtURyGiJJZKVEdFOsdKUCPTNEVFZq3zJ2R0G5wc2PZ5gvdTRFgm81zA==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.9.0.tgz", + "integrity": "sha512-NcMLjoFMXpsASZFxJ5h2HZRcEhDkvnNFOAKneP5RbKRzaWJN36NC4jqQHKwStIhGXu5mUWlUUk7ygdtrO8lbmw==", "dev": true }, "@webassemblyjs/helper-buffer": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.8.5.tgz", - "integrity": "sha512-Ri2R8nOS0U6G49Q86goFIPNgjyl6+oE1abW1pS84BuhP1Qcr5JqMwRFT3Ah3ADDDYGEgGs1iyb1DGX+kAi/c/Q==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.9.0.tgz", + "integrity": "sha512-qZol43oqhq6yBPx7YM3m9Bv7WMV9Eevj6kMi6InKOuZxhw+q9hOkvq5e/PpKSiLfyetpaBnogSbNCfBwyB00CA==", "dev": true }, "@webassemblyjs/helper-code-frame": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-code-frame/-/helper-code-frame-1.8.5.tgz", - "integrity": "sha512-VQAadSubZIhNpH46IR3yWO4kZZjMxN1opDrzePLdVKAZ+DFjkGD/rf4v1jap744uPVU6yjL/smZbRIIJTOUnKQ==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-code-frame/-/helper-code-frame-1.9.0.tgz", + "integrity": "sha512-ERCYdJBkD9Vu4vtjUYe8LZruWuNIToYq/ME22igL+2vj2dQ2OOujIZr3MEFvfEaqKoVqpsFKAGsRdBSBjrIvZA==", "dev": true, "requires": { - "@webassemblyjs/wast-printer": "1.8.5" + "@webassemblyjs/wast-printer": "1.9.0" } }, "@webassemblyjs/helper-fsm": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-fsm/-/helper-fsm-1.8.5.tgz", - "integrity": "sha512-kRuX/saORcg8se/ft6Q2UbRpZwP4y7YrWsLXPbbmtepKr22i8Z4O3V5QE9DbZK908dh5Xya4Un57SDIKwB9eow==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-fsm/-/helper-fsm-1.9.0.tgz", + "integrity": "sha512-OPRowhGbshCb5PxJ8LocpdX9Kl0uB4XsAjl6jH/dWKlk/mzsANvhwbiULsaiqT5GZGT9qinTICdj6PLuM5gslw==", "dev": true }, "@webassemblyjs/helper-module-context": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-module-context/-/helper-module-context-1.8.5.tgz", - "integrity": "sha512-/O1B236mN7UNEU4t9X7Pj38i4VoU8CcMHyy3l2cV/kIF4U5KoHXDVqcDuOs1ltkac90IM4vZdHc52t1x8Yfs3g==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-module-context/-/helper-module-context-1.9.0.tgz", + "integrity": "sha512-MJCW8iGC08tMk2enck1aPW+BE5Cw8/7ph/VGZxwyvGbJwjktKkDK7vy7gAmMDx88D7mhDTCNKAW5tED+gZ0W8g==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "mamacro": "^0.0.3" + "@webassemblyjs/ast": "1.9.0" } }, "@webassemblyjs/helper-wasm-bytecode": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.8.5.tgz", - "integrity": "sha512-Cu4YMYG3Ddl72CbmpjU/wbP6SACcOPVbHN1dI4VJNJVgFwaKf1ppeFJrwydOG3NDHxVGuCfPlLZNyEdIYlQ6QQ==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.9.0.tgz", + "integrity": "sha512-R7FStIzyNcd7xKxCZH5lE0Bqy+hGTwS3LJjuv1ZVxd9O7eHCedSdrId/hMOd20I+v8wDXEn+bjfKDLzTepoaUw==", "dev": true }, "@webassemblyjs/helper-wasm-section": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.8.5.tgz", - "integrity": "sha512-VV083zwR+VTrIWWtgIUpqfvVdK4ff38loRmrdDBgBT8ADXYsEZ5mPQ4Nde90N3UYatHdYoDIFb7oHzMncI02tA==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.9.0.tgz", + "integrity": "sha512-XnMB8l3ek4tvrKUUku+IVaXNHz2YsJyOOmz+MMkZvh8h1uSJpSen6vYnw3IoQ7WwEuAhL8Efjms1ZWjqh2agvw==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-buffer": "1.8.5", - "@webassemblyjs/helper-wasm-bytecode": "1.8.5", - "@webassemblyjs/wasm-gen": "1.8.5" + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-buffer": "1.9.0", + "@webassemblyjs/helper-wasm-bytecode": "1.9.0", + "@webassemblyjs/wasm-gen": "1.9.0" } }, "@webassemblyjs/ieee754": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.8.5.tgz", - "integrity": "sha512-aaCvQYrvKbY/n6wKHb/ylAJr27GglahUO89CcGXMItrOBqRarUMxWLJgxm9PJNuKULwN5n1csT9bYoMeZOGF3g==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.9.0.tgz", + "integrity": "sha512-dcX8JuYU/gvymzIHc9DgxTzUUTLexWwt8uCTWP3otys596io0L5aW02Gb1RjYpx2+0Jus1h4ZFqjla7umFniTg==", "dev": true, "requires": { "@xtuc/ieee754": "^1.2.0" } }, "@webassemblyjs/leb128": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.8.5.tgz", - "integrity": "sha512-plYUuUwleLIziknvlP8VpTgO4kqNaH57Y3JnNa6DLpu/sGcP6hbVdfdX5aHAV716pQBKrfuU26BJK29qY37J7A==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.9.0.tgz", + "integrity": "sha512-ENVzM5VwV1ojs9jam6vPys97B/S65YQtv/aanqnU7D8aSoHFX8GyhGg0CMfyKNIHBuAVjy3tlzd5QMMINa7wpw==", "dev": true, "requires": { "@xtuc/long": "4.2.2" } }, "@webassemblyjs/utf8": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.8.5.tgz", - "integrity": "sha512-U7zgftmQriw37tfD934UNInokz6yTmn29inT2cAetAsaU9YeVCveWEwhKL1Mg4yS7q//NGdzy79nlXh3bT8Kjw==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.9.0.tgz", + "integrity": "sha512-GZbQlWtopBTP0u7cHrEx+73yZKrQoBMpwkGEIqlacljhXCkVM1kMQge/Mf+csMJAjEdSwhOyLAS0AoR3AG5P8w==", "dev": true }, "@webassemblyjs/wasm-edit": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.8.5.tgz", - "integrity": "sha512-A41EMy8MWw5yvqj7MQzkDjU29K7UJq1VrX2vWLzfpRHt3ISftOXqrtojn7nlPsZ9Ijhp5NwuODuycSvfAO/26Q==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.9.0.tgz", + "integrity": "sha512-FgHzBm80uwz5M8WKnMTn6j/sVbqilPdQXTWraSjBwFXSYGirpkSWE2R9Qvz9tNiTKQvoKILpCuTjBKzOIm0nxw==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-buffer": "1.8.5", - "@webassemblyjs/helper-wasm-bytecode": "1.8.5", - "@webassemblyjs/helper-wasm-section": "1.8.5", - "@webassemblyjs/wasm-gen": "1.8.5", - "@webassemblyjs/wasm-opt": "1.8.5", - "@webassemblyjs/wasm-parser": "1.8.5", - "@webassemblyjs/wast-printer": "1.8.5" + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-buffer": "1.9.0", + "@webassemblyjs/helper-wasm-bytecode": "1.9.0", + "@webassemblyjs/helper-wasm-section": "1.9.0", + "@webassemblyjs/wasm-gen": "1.9.0", + "@webassemblyjs/wasm-opt": "1.9.0", + "@webassemblyjs/wasm-parser": "1.9.0", + "@webassemblyjs/wast-printer": "1.9.0" } }, "@webassemblyjs/wasm-gen": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.8.5.tgz", - "integrity": "sha512-BCZBT0LURC0CXDzj5FXSc2FPTsxwp3nWcqXQdOZE4U7h7i8FqtFK5Egia6f9raQLpEKT1VL7zr4r3+QX6zArWg==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.9.0.tgz", + "integrity": "sha512-cPE3o44YzOOHvlsb4+E9qSqjc9Qf9Na1OO/BHFy4OI91XDE14MjFN4lTMezzaIWdPqHnsTodGGNP+iRSYfGkjA==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-wasm-bytecode": "1.8.5", - "@webassemblyjs/ieee754": "1.8.5", - "@webassemblyjs/leb128": "1.8.5", - "@webassemblyjs/utf8": "1.8.5" + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-wasm-bytecode": "1.9.0", + "@webassemblyjs/ieee754": "1.9.0", + "@webassemblyjs/leb128": "1.9.0", + "@webassemblyjs/utf8": "1.9.0" } }, "@webassemblyjs/wasm-opt": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.8.5.tgz", - "integrity": "sha512-HKo2mO/Uh9A6ojzu7cjslGaHaUU14LdLbGEKqTR7PBKwT6LdPtLLh9fPY33rmr5wcOMrsWDbbdCHq4hQUdd37Q==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.9.0.tgz", + "integrity": "sha512-Qkjgm6Anhm+OMbIL0iokO7meajkzQD71ioelnfPEj6r4eOFuqm4YC3VBPqXjFyyNwowzbMD+hizmprP/Fwkl2A==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-buffer": "1.8.5", - "@webassemblyjs/wasm-gen": "1.8.5", - "@webassemblyjs/wasm-parser": "1.8.5" + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-buffer": "1.9.0", + "@webassemblyjs/wasm-gen": "1.9.0", + "@webassemblyjs/wasm-parser": "1.9.0" } }, "@webassemblyjs/wasm-parser": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.8.5.tgz", - "integrity": "sha512-pi0SYE9T6tfcMkthwcgCpL0cM9nRYr6/6fjgDtL6q/ZqKHdMWvxitRi5JcZ7RI4SNJJYnYNaWy5UUrHQy998lw==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.9.0.tgz", + "integrity": "sha512-9+wkMowR2AmdSWQzsPEjFU7njh8HTO5MqO8vjwEHuM+AMHioNqSBONRdr0NQQ3dVQrzp0s8lTcYqzUdb7YgELA==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-api-error": "1.8.5", - "@webassemblyjs/helper-wasm-bytecode": "1.8.5", - "@webassemblyjs/ieee754": "1.8.5", - "@webassemblyjs/leb128": "1.8.5", - "@webassemblyjs/utf8": "1.8.5" + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-api-error": "1.9.0", + "@webassemblyjs/helper-wasm-bytecode": "1.9.0", + "@webassemblyjs/ieee754": "1.9.0", + "@webassemblyjs/leb128": "1.9.0", + "@webassemblyjs/utf8": "1.9.0" } }, "@webassemblyjs/wast-parser": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-parser/-/wast-parser-1.8.5.tgz", - "integrity": "sha512-daXC1FyKWHF1i11obK086QRlsMsY4+tIOKgBqI1lxAnkp9xe9YMcgOxm9kLe+ttjs5aWV2KKE1TWJCN57/Btsg==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-parser/-/wast-parser-1.9.0.tgz", + "integrity": "sha512-qsqSAP3QQ3LyZjNC/0jBJ/ToSxfYJ8kYyuiGvtn/8MK89VrNEfwj7BPQzJVHi0jGTRK2dGdJ5PRqhtjzoww+bw==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/floating-point-hex-parser": "1.8.5", - "@webassemblyjs/helper-api-error": "1.8.5", - "@webassemblyjs/helper-code-frame": "1.8.5", - "@webassemblyjs/helper-fsm": "1.8.5", + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/floating-point-hex-parser": "1.9.0", + "@webassemblyjs/helper-api-error": "1.9.0", + "@webassemblyjs/helper-code-frame": "1.9.0", + "@webassemblyjs/helper-fsm": "1.9.0", "@xtuc/long": "4.2.2" } }, "@webassemblyjs/wast-printer": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.8.5.tgz", - "integrity": "sha512-w0U0pD4EhlnvRyeJzBqaVSJAo9w/ce7/WPogeXLzGkO6hzhr4GnQIZ4W4uUt5b9ooAaXPtnXlj0gzsXEOUNYMg==", + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.9.0.tgz", + "integrity": "sha512-2J0nE95rHXHyQ24cWjMKJ1tqB/ds8z/cyeOZxJhcb+rW+SQASVjuznUSmdz5GpVJTzU8JkhYut0D3siFDD6wsA==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/wast-parser": "1.8.5", + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/wast-parser": "1.9.0", "@xtuc/long": "4.2.2" } }, @@ -7989,12 +7988,6 @@ "semver": "^5.6.0" } }, - "mamacro": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/mamacro/-/mamacro-0.0.3.tgz", - "integrity": "sha512-qMEwh+UujcQ+kbz3T6V+wAmO2U8veoq2w+3wY8MquqwVA3jChfwY+Tk52GZKDfACEPjuZ7r2oJLejwpt8jtwTA==", - "dev": true - }, "map-age-cleaner": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/map-age-cleaner/-/map-age-cleaner-0.1.3.tgz", @@ -12246,12 +12239,12 @@ } }, "watchpack": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-1.6.0.tgz", - "integrity": "sha512-i6dHe3EyLjMmDlU1/bGQpEw25XSjkJULPuAVKCbNRefQVq48yXKUpwg538F7AZTf9kyr57zj++pQFltUa5H7yA==", + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-1.6.1.tgz", + "integrity": "sha512-+IF9hfUFOrYOOaKyfaI7h7dquUIOgyEMoQMLA7OP5FxegKA2+XdXThAZ9TU2kucfhDH7rfMHs1oPYziVGWRnZA==", "dev": true, "requires": { - "chokidar": "^2.0.2", + "chokidar": "^2.1.8", "graceful-fs": "^4.1.2", "neo-async": "^2.5.0" } @@ -12272,15 +12265,15 @@ "dev": true }, "webpack": { - "version": "4.42.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-4.42.0.tgz", - "integrity": "sha512-EzJRHvwQyBiYrYqhyjW9AqM90dE4+s1/XtCfn7uWg6cS72zH+2VPFAlsnW0+W0cDi0XRjNKUMoJtpSi50+Ph6w==", + "version": "4.42.1", + "resolved": "https://registry.npmjs.org/webpack/-/webpack-4.42.1.tgz", + "integrity": "sha512-SGfYMigqEfdGchGhFFJ9KyRpQKnipvEvjc1TwrXEPCM6H5Wywu10ka8o3KGrMzSMxMQKt8aCHUFh5DaQ9UmyRg==", "dev": true, "requires": { - "@webassemblyjs/ast": "1.8.5", - "@webassemblyjs/helper-module-context": "1.8.5", - "@webassemblyjs/wasm-edit": "1.8.5", - "@webassemblyjs/wasm-parser": "1.8.5", + "@webassemblyjs/ast": "1.9.0", + "@webassemblyjs/helper-module-context": "1.9.0", + "@webassemblyjs/wasm-edit": "1.9.0", + "@webassemblyjs/wasm-parser": "1.9.0", "acorn": "^6.2.1", "ajv": "^6.10.2", "ajv-keywords": "^3.4.1", @@ -12292,7 +12285,7 @@ "loader-utils": "^1.2.3", "memory-fs": "^0.4.1", "micromatch": "^3.1.10", - "mkdirp": "^0.5.1", + "mkdirp": "^0.5.3", "neo-async": "^2.6.1", "node-libs-browser": "^2.2.1", "schema-utils": "^1.0.0", @@ -12326,6 +12319,21 @@ "integrity": "sha512-8UEa58QDLauDNfpbrX55Q9jrGHThw2ZMdOky5Gl1CDtVeJDPVrG4Jxx1N8jw2gkWaff5UUuX1KJd+9zGe2B+ZA==", "dev": true }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, + "mkdirp": { + "version": "0.5.4", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.4.tgz", + "integrity": "sha512-iG9AK/dJLtJ0XNgTuDbSyNS3zECqDlAhnQW4CsNxBG3LQJBbHmRX1egw39DmtOdCAqY+dKXV+sgPgilNWUKMVw==", + "dev": true, + "requires": { + "minimist": "^1.2.5" + } + }, "neo-async": { "version": "2.6.1", "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.1.tgz", diff --git a/package.json b/package.json index 2eca898191..932a509439 100644 --- a/package.json +++ b/package.json @@ -101,7 +101,7 @@ "typescript": "3.5.3", "url-polyfill": "^1.1.5", "walk": "^2.3.9", - "webpack": "4.42.0", + "webpack": "4.42.1", "webpack-cli": "^3.3.2", "webpack-dev-middleware": "^3.6.2", "webpack-dev-server": "^3.3.1", From 6ca6c70aac879a2e8e0c335df7d40dbd01043d92 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 30 Mar 2020 08:56:40 +0000 Subject: [PATCH 073/119] Bump buble from 0.19.8 to 0.20.0 Bumps [buble](https://github.com/bublejs/buble) from 0.19.8 to 0.20.0. - [Release notes](https://github.com/bublejs/buble/releases) - [Changelog](https://github.com/bublejs/buble/blob/master/CHANGELOG.md) - [Commits](https://github.com/bublejs/buble/compare/v0.19.8...v0.20.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 65 +++++++++++++++++++++++------------------------ package.json | 2 +- 2 files changed, 33 insertions(+), 34 deletions(-) diff --git a/package-lock.json b/package-lock.json index 450a9667f9..84aaa30d67 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2024,9 +2024,9 @@ "dev": true }, "acorn-jsx": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.0.1.tgz", - "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.2.0.tgz", + "integrity": "sha512-HiUX/+K2YpkpJ+SzBffkM/AQ2YE03S0U1kjTLVpoJdhZMOWy8qvXVN9JdLqv2QsaQ6MPYQIuNmwD8zOiYUofLQ==", "dev": true }, "after": { @@ -2951,29 +2951,34 @@ } }, "buble": { - "version": "0.19.8", - "resolved": "https://registry.npmjs.org/buble/-/buble-0.19.8.tgz", - "integrity": "sha512-IoGZzrUTY5fKXVkgGHw3QeXFMUNBFv+9l8a4QJKG1JhG3nCMHTdEX1DCOg8568E2Q9qvAQIiSokv6Jsgx8p2cA==", + "version": "0.20.0", + "resolved": "https://registry.npmjs.org/buble/-/buble-0.20.0.tgz", + "integrity": "sha512-/1gnaMQE8xvd5qsNBl+iTuyjJ9XxeaVxAMF86dQ4EyxFJOZtsgOS8Ra+7WHgZTam5IFDtt4BguN0sH0tVTKrOw==", "dev": true, "requires": { - "acorn": "^6.1.1", + "acorn": "^6.4.1", "acorn-dynamic-import": "^4.0.0", - "acorn-jsx": "^5.0.1", + "acorn-jsx": "^5.2.0", "chalk": "^2.4.2", - "magic-string": "^0.25.3", - "minimist": "^1.2.0", - "os-homedir": "^2.0.0", - "regexpu-core": "^4.5.4" + "magic-string": "^0.25.7", + "minimist": "^1.2.5", + "regexpu-core": "4.5.4" }, "dependencies": { "magic-string": { - "version": "0.25.4", - "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.4.tgz", - "integrity": "sha512-oycWO9nEVAP2RVPbIoDoA4Y7LFIJ3xRYov93gAyJhZkET1tNuB0u7uWkZS2LpBWTJUWnmau/To8ECWRC+jKNfw==", + "version": "0.25.7", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.7.tgz", + "integrity": "sha512-4CrMT5DOHTDk4HYDlzmwu4FVCcIYI8gauveasrdCu2IKIFOJ3f0v/8MDGJCDL9oD2ppz/Av1b0Nj345H9M+XIA==", "dev": true, "requires": { "sourcemap-codec": "^1.4.4" } + }, + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true } } }, @@ -9108,12 +9113,6 @@ "integrity": "sha1-hUNzx/XCMVkU/Jv8a9gjj92h7Cc=", "dev": true }, - "os-homedir": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-2.0.0.tgz", - "integrity": "sha512-saRNz0DSC5C/I++gFIaJTXoFJMRwiP5zHar5vV3xQ2TkgEw6hDCcU5F272JjUylpiVgBrZNQHnfjkLabTfb92Q==", - "dev": true - }, "os-locale": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-3.1.0.tgz", @@ -9872,9 +9871,9 @@ "dev": true }, "regenerate-unicode-properties": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-8.0.2.tgz", - "integrity": "sha512-SbA/iNrBUf6Pv2zU8Ekv1Qbhv92yxL4hiDa2siuxs4KKn4oOoMDHXjAf7+Nz9qinUQ46B1LcWEi/PhJfPWpZWQ==", + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-8.2.0.tgz", + "integrity": "sha512-F9DjY1vKLo/tPePDycuH3dn9H1OTPIkVD9Kz4LODu+F2C75mgjAJ7x/gwy6ZcSNRAAkhNlJSOHRe8k3p+K9WhA==", "dev": true, "requires": { "regenerate": "^1.4.0" @@ -9936,15 +9935,15 @@ } }, "regjsgen": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.5.0.tgz", - "integrity": "sha512-RnIrLhrXCX5ow/E5/Mh2O4e/oa1/jW0eaBKTSy3LaCj+M3Bqvm97GWDp2yUtzIs4LEn65zR2yiYGFqb2ApnzDA==", + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.5.1.tgz", + "integrity": "sha512-5qxzGZjDs9w4tzT3TPhCJqWdCc3RLYwy9J2NB0nm5Lz+S273lvWcpjaTGHsT1dc6Hhfq41uSEOw8wBmxrKOuyg==", "dev": true }, "regjsparser": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.6.0.tgz", - "integrity": "sha512-RQ7YyokLiQBomUJuUG8iGVvkgOLxwyZM8k6d3q5SAXpg4r5TZJZigKFvC6PpD+qQ98bCDC5YelPeA3EucDoNeQ==", + "version": "0.6.4", + "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.6.4.tgz", + "integrity": "sha512-64O87/dPDgfk8/RQqC4gkZoGyyWFIEUTTh80CU6CWuK5vkCGyekIx+oKcEIYtP/RAxSQltCZHCNu/mdd7fqlJw==", "dev": true, "requires": { "jsesc": "~0.5.0" @@ -11976,9 +11975,9 @@ } }, "unicode-match-property-value-ecmascript": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-1.1.0.tgz", - "integrity": "sha512-hDTHvaBk3RmFzvSl0UVrUmC3PuW9wKVnpoUDYH0JDkSIovzw+J5viQmeYHxVSBptubnr7PbH2e0fnpDRQnQl5g==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-1.2.0.tgz", + "integrity": "sha512-wjuQHGQVofmSJv1uVISKLE5zO2rNGzM/KCYZch/QQvez7C1hUhBIuZ701fYXExuufJFMPhv2SyL8CyoIfMLbIQ==", "dev": true }, "unicode-property-aliases-ecmascript": { diff --git a/package.json b/package.json index 2eca898191..5008aa39f8 100644 --- a/package.json +++ b/package.json @@ -54,7 +54,7 @@ "@types/pbf": "^3.0.2", "@types/topojson-specification": "^1.0.1", "babel-loader": "^8.0.5", - "buble": "^0.19.7", + "buble": "^0.20.0", "buble-loader": "^0.5.1", "chaikin-smooth": "^1.0.4", "clean-css-cli": "4.3.0", From e583e0775ddbb2f868780aaa4a0a57bd90e3ac2d Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 30 Mar 2020 08:57:39 +0000 Subject: [PATCH 074/119] Bump ol-mapbox-style from 6.1.0 to 6.1.1 Bumps [ol-mapbox-style](https://github.com/openlayers/ol-mapbox-style) from 6.1.0 to 6.1.1. - [Release notes](https://github.com/openlayers/ol-mapbox-style/releases) - [Changelog](https://github.com/openlayers/ol-mapbox-style/blob/master/CHANGELOG.md) - [Commits](https://github.com/openlayers/ol-mapbox-style/compare/v6.1.0...v6.1.1) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/package-lock.json b/package-lock.json index 450a9667f9..8aaa829acb 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1606,12 +1606,13 @@ "dev": true }, "@mapbox/mapbox-gl-style-spec": { - "version": "13.12.0", - "resolved": "https://registry.npmjs.org/@mapbox/mapbox-gl-style-spec/-/mapbox-gl-style-spec-13.12.0.tgz", - "integrity": "sha512-tRSvlYUI73LOkvS1iQhVwnltoI/QC4ZaLOAS6NM6zx0NwJfsGUJDPucsaKif8l7Sce1ECLd8LYs1MRCyJjdo5Q==", + "version": "13.13.0", + "resolved": "https://registry.npmjs.org/@mapbox/mapbox-gl-style-spec/-/mapbox-gl-style-spec-13.13.0.tgz", + "integrity": "sha512-PBXa/Bw2G87NZckBZqY3omI3THF5MYQQY5B1IZWVLI7Ujsy149cjC8Sm1Ub1BgAnyslepdjtwWVS43IOjVYmUw==", "dev": true, "requires": { "@mapbox/jsonlint-lines-primitives": "~2.0.2", + "@mapbox/point-geometry": "^0.1.0", "@mapbox/unitbezier": "^0.0.0", "csscolorparser": "~1.0.2", "json-stringify-pretty-compact": "^2.0.0", @@ -1628,6 +1629,12 @@ } } }, + "@mapbox/point-geometry": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/@mapbox/point-geometry/-/point-geometry-0.1.0.tgz", + "integrity": "sha1-ioP5M1x4YO/6Lu7KJUMyqgru2PI=", + "dev": true + }, "@mapbox/unitbezier": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/@mapbox/unitbezier/-/unitbezier-0.0.0.tgz", @@ -9003,12 +9010,12 @@ "dev": true }, "ol-mapbox-style": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ol-mapbox-style/-/ol-mapbox-style-6.1.0.tgz", - "integrity": "sha512-52nrvbYi8+Zkn4+4EZ92ZJMCLW50RKCgtPm7LNXyZJkz/PCtRZJ440Jy4hPWMON7swV2O9Xjyg+HD8Xv00VFgw==", + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/ol-mapbox-style/-/ol-mapbox-style-6.1.1.tgz", + "integrity": "sha512-0Hgz2BX2tWe1ZNPMLpJkLdm3XI6ILrFbgmJIvdrlDYRce2ul1mXLmkJmbyLFs2tozsBJDcPJmI55UsKbiKg6ow==", "dev": true, "requires": { - "@mapbox/mapbox-gl-style-spec": "^13.11.0", + "@mapbox/mapbox-gl-style-spec": "13.13.0", "mapbox-to-css-font": "^2.4.0", "webfont-matcher": "^1.1.0" } From c92f72ac3f16da7295701ffe83958bac3bdd0527 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 30 Mar 2020 08:59:06 +0000 Subject: [PATCH 075/119] Bump rollup from 2.1.0 to 2.3.0 Bumps [rollup](https://github.com/rollup/rollup) from 2.1.0 to 2.3.0. - [Release notes](https://github.com/rollup/rollup/releases) - [Changelog](https://github.com/rollup/rollup/blob/master/CHANGELOG.md) - [Commits](https://github.com/rollup/rollup/compare/v2.1.0...v2.3.0) Signed-off-by: dependabot-preview[bot] --- package-lock.json | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/package-lock.json b/package-lock.json index 450a9667f9..3ed11bd1e9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10163,9 +10163,9 @@ } }, "rollup": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.1.0.tgz", - "integrity": "sha512-gfE1455AEazVVTJoeQtcOq/U6GSxwoj4XPSWVsuWmgIxj7sBQNLDOSA82PbdMe+cP8ql8fR1jogPFe8Wg8g4SQ==", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.3.0.tgz", + "integrity": "sha512-nIq2Z9YwNbEfqTlAXe/tVl8CwUsjX/8Q5Jxlx+JRoYCu5keKLc6k0zyt11sM6WtCDxhmmJEIosFy9y26ZFRx6w==", "dev": true, "requires": { "fsevents": "~2.1.2" From 772741cd0e3c059863f8c34ff81ebedff20b3887 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sat, 14 Mar 2020 10:14:28 +0000 Subject: [PATCH 076/119] Always load frameState extent for graticule layers do not call graticule loader with wrapped projection extent --- src/ol/renderer/canvas/VectorLayer.js | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index 591ea95f83..d9e5e308e2 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -363,6 +363,8 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { vectorLayerRenderBuffer * resolution); const projectionExtent = viewState.projection.getExtent(); + let loadExtent = extent.slice(); + if (vectorSource.getWrapX() && viewState.projection.canWrapX() && !containsExtent(projectionExtent, frameState.extent)) { // For the replay group, we need an extent that intersects the real world @@ -378,6 +380,10 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { center[0] -= (worldsAway * worldWidth); } + if (typeof /** @type {?} */ (vectorLayer).getMeridians !== 'function') { + loadExtent = extent; + } + if (!this.dirty_ && this.renderedResolution_ == resolution && this.renderedRevision_ == vectorLayerRevision && @@ -398,10 +404,10 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const userProjection = getUserProjection(); let userTransform; if (userProjection) { - vectorSource.loadFeatures(toUserExtent(extent, projection), resolution, userProjection); + vectorSource.loadFeatures(toUserExtent(loadExtent, projection), resolution, userProjection); userTransform = getTransformFromProjections(userProjection, projection); } else { - vectorSource.loadFeatures(extent, resolution, projection); + vectorSource.loadFeatures(loadExtent, resolution, projection); } const squaredTolerance = getSquaredRenderTolerance(resolution, pixelRatio); From bad0ff38ca2a690b045e94c86fab9e449c8ed5a0 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sat, 14 Mar 2020 10:37:03 +0000 Subject: [PATCH 077/119] handle wrapX without calculating excess meridians avoid calculating more meridians or longer parallels than necessary when viewport extent includes a wrapped world --- src/ol/layer/Graticule.js | 112 ++++++++++++++++++++++++++------------ 1 file changed, 76 insertions(+), 36 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 6bc7360dfa..0e3f073eb1 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -717,6 +717,22 @@ class Graticule extends VectorLayer { return; } + let wrapX = false; + const projectionExtent = this.projection_.getExtent(); + const worldWidth = getWidth(projectionExtent); + if (this.getSource().getWrapX() && this.projection_.canWrapX() && !containsExtent(projectionExtent, extent)) { + if (getWidth(extent) >= worldWidth) { + extent[0] = projectionExtent[0]; + extent[2] = projectionExtent[2]; + } else { + const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); + center[0] -= (worldsAway * worldWidth); + extent[0] -= (worldsAway * worldWidth); + extent[2] -= (worldsAway * worldWidth); + wrapX = true; + } + } + // Constrain the center to fit into the extent available to the graticule const validCenterP = [ @@ -740,44 +756,56 @@ class Graticule extends VectorLayer { // Limit the extent to fit into the extent available to the graticule - const validExtentP = [ - clamp(extent[0], this.minX_, this.maxX_), - clamp(extent[1], this.minY_, this.maxY_), - clamp(extent[2], this.minX_, this.maxX_), - clamp(extent[3], this.minY_, this.maxY_) - ]; + let validExtentP = extent; + if (!wrapX) { + validExtentP = [ + clamp(extent[0], this.minX_, this.maxX_), + clamp(extent[1], this.minY_, this.maxY_), + clamp(extent[2], this.minX_, this.maxX_), + clamp(extent[3], this.minY_, this.maxY_) + ]; + } // Transform the extent to get the lon lat ranges for the edges of the extent const validExtent = applyTransform(validExtentP, this.toLonLatTransform_, undefined, 8); - // Check if extremities of the world extent lie inside the extent - // (for example the pole in a polar projection) - // and extend the extent as appropriate + let maxLat = validExtent[3]; + let maxLon = validExtent[2]; + let minLat = validExtent[1]; + let minLon = validExtent[0]; - if (containsCoordinate(validExtentP, this.bottomLeft_)) { - validExtent[0] = this.minLon_; - validExtent[1] = this.minLat_; - } - if (containsCoordinate(validExtentP, this.bottomRight_)) { - validExtent[2] = this.maxLon_; - validExtent[1] = this.minLat_; - } - if (containsCoordinate(validExtentP, this.topLeft_)) { - validExtent[0] = this.minLon_; - validExtent[3] = this.maxLat_; - } - if (containsCoordinate(validExtentP, this.topRight_)) { - validExtent[2] = this.maxLon_; - validExtent[3] = this.maxLat_; - } + if (!wrapX) { - // The transformed center may also extend the lon lat ranges used for rendering + // Check if extremities of the world extent lie inside the extent + // (for example the pole in a polar projection) + // and extend the extent as appropriate - const maxLat = clamp(validExtent[3], centerLat, this.maxLat_); - const maxLon = clamp(validExtent[2], centerLon, this.maxLon_); - const minLat = clamp(validExtent[1], this.minLat_, centerLat); - const minLon = clamp(validExtent[0], this.minLon_, centerLon); + if (containsCoordinate(validExtentP, this.bottomLeft_)) { + minLon = this.minLon_; + minLat = this.minLat_; + } + if (containsCoordinate(validExtentP, this.bottomRight_)) { + maxLon = this.maxLon_; + minLat = this.minLat_; + } + if (containsCoordinate(validExtentP, this.topLeft_)) { + minLon = this.minLon_; + maxLat = this.maxLat_; + } + if (containsCoordinate(validExtentP, this.topRight_)) { + maxLon = this.maxLon_; + maxLat = this.maxLat_; + } + + // The transformed center may also extend the lon lat ranges used for rendering + + maxLat = clamp(maxLat, centerLat, this.maxLat_); + maxLon = clamp(maxLon, centerLon, this.maxLon_); + minLat = clamp(minLat, this.minLat_, centerLat); + minLon = clamp(minLon, this.minLon_, centerLon); + + } // Create meridians @@ -787,17 +815,29 @@ class Graticule extends VectorLayer { idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, 0); cnt = 0; - while (lon != this.minLon_ && cnt++ < maxLines) { - lon = Math.max(lon - interval, this.minLon_); - idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + if (wrapX) { + while ((lon -= interval) >= minLon && cnt++ < maxLines) { + idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + } + } else { + while (lon != this.minLon_ && cnt++ < maxLines) { + lon = Math.max(lon - interval, this.minLon_); + idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + } } lon = clamp(centerLon, this.minLon_, this.maxLon_); cnt = 0; - while (lon != this.maxLon_ && cnt++ < maxLines) { - lon = Math.min(lon + interval, this.maxLon_); - idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + if (wrapX) { + while ((lon += interval) <= maxLon && cnt++ < maxLines) { + idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + } + } else { + while (lon != this.maxLon_ && cnt++ < maxLines) { + lon = Math.min(lon + interval, this.maxLon_); + idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); + } } this.meridians_.length = idx; From 516a75ae226c8bbdcb418437e825601451175f0a Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sun, 15 Mar 2020 11:44:30 +0000 Subject: [PATCH 078/119] Always load frameState extent for graticule layers reorder and comment --- src/ol/renderer/canvas/VectorLayer.js | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index d9e5e308e2..3429f64106 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -361,9 +361,8 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const center = viewState.center.slice(); const extent = buffer(frameStateExtent, vectorLayerRenderBuffer * resolution); - const projectionExtent = viewState.projection.getExtent(); - let loadExtent = extent.slice(); + const projectionExtent = viewState.projection.getExtent(); if (vectorSource.getWrapX() && viewState.projection.canWrapX() && !containsExtent(projectionExtent, frameState.extent)) { @@ -376,14 +375,14 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const gutter = Math.max(getWidth(extent) / 2, worldWidth); extent[0] = projectionExtent[0] - gutter; extent[2] = projectionExtent[2] + gutter; + // Except for Graticule use this for loading features + if (typeof /** @type {?} */ (vectorLayer).getMeridians !== 'function') { + loadExtent = extent; + } const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); center[0] -= (worldsAway * worldWidth); } - if (typeof /** @type {?} */ (vectorLayer).getMeridians !== 'function') { - loadExtent = extent; - } - if (!this.dirty_ && this.renderedResolution_ == resolution && this.renderedRevision_ == vectorLayerRevision && From f6ede1a9c0895bfa946e636d6566427a5e5b473c Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Wed, 18 Mar 2020 13:28:21 +0000 Subject: [PATCH 079/119] handle wrapX without calculating excess meridians override extent validation only if the extent includes parts of two worlds --- src/ol/layer/Graticule.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 0e3f073eb1..15ba7cd2a1 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -729,7 +729,7 @@ class Graticule extends VectorLayer { center[0] -= (worldsAway * worldWidth); extent[0] -= (worldsAway * worldWidth); extent[2] -= (worldsAway * worldWidth); - wrapX = true; + wrapX = !containsExtent(projectionExtent, extent); } } From f6bbf414a8de864801d31c136ab8c3816c07fe7d Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sat, 28 Mar 2020 20:59:23 +0000 Subject: [PATCH 080/119] Add loadWrapX option and getter --- src/ol/source/Vector.js | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/src/ol/source/Vector.js b/src/ol/source/Vector.js index 49ac34296b..edf1c4e25d 100644 --- a/src/ol/source/Vector.js +++ b/src/ol/source/Vector.js @@ -146,6 +146,10 @@ export class VectorSourceEvent extends Event { * @property {boolean} [wrapX=true] Wrap the world horizontally. For vector editing across the * -180° and 180° meridians to work properly, this should be set to `false`. The * resulting geometry coordinates will then exceed the world bounds. + * @property {boolean} [loadWrapX=true] Call the loader with one world width either side + * of the projection extent when the world is wrapped horizontally. This allows features + * to be loaded in a single request, but may be inefficient. If `false` only the viewport + * extent is used and the loader must determine the appropriate real world requests. */ @@ -190,7 +194,13 @@ class VectorSource extends Source { * @private * @type {boolean} */ - this.overlaps_ = options.overlaps == undefined ? true : options.overlaps; + this.loadWrapX_ = options.loadWrapX === undefined ? true : options.loadWrapX; + + /** + * @private + * @type {boolean} + */ + this.overlaps_ = options.overlaps === undefined ? true : options.overlaps; /** * @private @@ -801,6 +811,14 @@ class VectorSource extends Source { } + /** + * @return {boolean} The loadWrapX option used to construct the source. + */ + getLoadWrapX() { + return this.loadWrapX_; + } + + /** * @return {boolean} The source can have overlapping geometries. */ From b560dab513bd60020df510d70ff32975de031ae8 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sat, 28 Mar 2020 21:02:32 +0000 Subject: [PATCH 081/119] Set loadWrapX: false in source --- src/ol/layer/Graticule.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 15ba7cd2a1..aa13cd8fee 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -437,7 +437,8 @@ class Graticule extends VectorLayer { features: new Collection(), overlaps: false, useSpatialIndex: false, - wrapX: options.wrapX + wrapX: options.wrapX, + loadWrapX: false }) ); From 3b760dc3083965f77ebcd2473974ef5361ce4fc0 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sat, 28 Mar 2020 21:10:41 +0000 Subject: [PATCH 082/119] Use getLoadWrapX() to determine extent to load --- src/ol/renderer/canvas/VectorLayer.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index 3429f64106..bdfe6c2e5b 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -375,8 +375,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const gutter = Math.max(getWidth(extent) / 2, worldWidth); extent[0] = projectionExtent[0] - gutter; extent[2] = projectionExtent[2] + gutter; - // Except for Graticule use this for loading features - if (typeof /** @type {?} */ (vectorLayer).getMeridians !== 'function') { + if (vectorSource.getLoadWrapX()) { loadExtent = extent; } const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); From 67c37c2163af4bb573b0106962c31ddc5e74b800 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sun, 29 Mar 2020 16:54:10 +0100 Subject: [PATCH 083/119] Test extents passed to loader --- .../ol/renderer/canvas/vectorlayer.test.js | 102 +++++++++++++++++- 1 file changed, 99 insertions(+), 3 deletions(-) diff --git a/test/spec/ol/renderer/canvas/vectorlayer.test.js b/test/spec/ol/renderer/canvas/vectorlayer.test.js index a766fdb767..575d7c11a8 100644 --- a/test/spec/ol/renderer/canvas/vectorlayer.test.js +++ b/test/spec/ol/renderer/canvas/vectorlayer.test.js @@ -6,6 +6,7 @@ import Circle from '../../../../../src/ol/geom/Circle.js'; import Point from '../../../../../src/ol/geom/Point.js'; import {fromExtent} from '../../../../../src/ol/geom/Polygon.js'; import VectorLayer from '../../../../../src/ol/layer/Vector.js'; +import {bbox as bboxStrategy} from '../../../../../src/ol/loadingstrategy.js'; import {get as getProjection} from '../../../../../src/ol/proj.js'; import {checkedFonts} from '../../../../../src/ol/render/canvas.js'; import CanvasVectorLayerRenderer from '../../../../../src/ol/renderer/canvas/VectorLayer.js'; @@ -220,17 +221,25 @@ describe('ol.renderer.canvas.VectorLayer', function() { }); describe('#prepareFrame and #compose', function() { - let frameState, projExtent, renderer, worldWidth, buffer; + let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; + const loader = function(extent) { + loadExtent = extent; + } beforeEach(function() { const layer = new VectorLayer({ - source: new VectorSource({wrapX: true}) + source: new VectorSource({ + wrapX: true, + loader: loader, + strategy: bboxStrategy + }) }); renderer = new CanvasVectorLayerRenderer(layer); const projection = getProjection('EPSG:3857'); projExtent = projection.getExtent(); worldWidth = getWidth(projExtent); buffer = layer.getRenderBuffer(); + loadExtent = undefined; frameState = { viewHints: [], viewState: { @@ -251,7 +260,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - + expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); }); it('sets correct extent for viewport less than 1 world wide', function() { @@ -263,6 +272,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); + expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); }); it('sets correct extent for viewport more than 1 world wide', function() { @@ -274,6 +284,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); + expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); }); it('sets correct extent for viewport more than 2 worlds wide', function() { @@ -287,6 +298,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - 2 * worldWidth - 10000, -10000, projExtent[2] + 2 * worldWidth + 10000, 10000 ], buffer)); + expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); }); it('sets replayGroupChanged correctly', function() { @@ -319,6 +331,90 @@ describe('ol.renderer.canvas.VectorLayer', function() { }); + describe('#prepareFrame with a loadWrapX: false source', function() { + let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; + const loader = function(extent) { + loadExtent = extent; + } + + beforeEach(function() { + const layer = new VectorLayer({ + source: new VectorSource({ + wrapX: true, + loadWrapX: false, + loader: loader, + strategy: bboxStrategy + }) + }); + renderer = new CanvasVectorLayerRenderer(layer); + const projection = getProjection('EPSG:3857'); + projExtent = projection.getExtent(); + worldWidth = getWidth(projExtent); + buffer = layer.getRenderBuffer(); + loadExtent = undefined; + frameState = { + viewHints: [], + viewState: { + center: [0, 0], + projection: projection, + resolution: 1, + rotation: 0 + } + }; + }); + + it('loads correct extent for small viewport near dateline', function() { + + frameState.extent = + [projExtent[0] - 10000, -10000, projExtent[0] + 10000, 10000]; + renderer.prepareFrame(frameState); + expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ + projExtent[0] - worldWidth + buffer, + -10000, projExtent[2] + worldWidth - buffer, 10000 + ], buffer)); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + }); + + it('loads correct extent for viewport less than 1 world wide', function() { + + frameState.extent = + [projExtent[0] - 10000, -10000, projExtent[1] - 10000, 10000]; + renderer.prepareFrame(frameState); + expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ + projExtent[0] - worldWidth + buffer, + -10000, projExtent[2] + worldWidth - buffer, 10000 + ], buffer)); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + }); + + it('loads correct extent for viewport more than 1 world wide', function() { + + frameState.extent = + [2 * projExtent[0] - 10000, -10000, 2 * projExtent[1] + 10000, 10000]; + renderer.prepareFrame(frameState); + expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ + projExtent[0] - worldWidth + buffer, + -10000, projExtent[2] + worldWidth - buffer, 10000 + ], buffer)); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + }); + + it('loads correct extent for viewport more than 2 worlds wide', function() { + + frameState.extent = [ + projExtent[0] - 2 * worldWidth - 10000, + -10000, projExtent[1] + 2 * worldWidth + 10000, 10000 + ]; + renderer.prepareFrame(frameState); + expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ + projExtent[0] - 2 * worldWidth - 10000, + -10000, projExtent[2] + 2 * worldWidth + 10000, 10000 + ], buffer)); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + }); + + }); + describe('hit detection', function() { it('with no fill and transparent fill', function() { From 0c9324f398df0150d1afe5f83d8a98c9fa5a0025 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sun, 29 Mar 2020 16:58:57 +0100 Subject: [PATCH 084/119] Test extents passed to loader --- test/spec/ol/renderer/canvas/vectorlayer.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/spec/ol/renderer/canvas/vectorlayer.test.js b/test/spec/ol/renderer/canvas/vectorlayer.test.js index 575d7c11a8..f163a6b4cf 100644 --- a/test/spec/ol/renderer/canvas/vectorlayer.test.js +++ b/test/spec/ol/renderer/canvas/vectorlayer.test.js @@ -224,7 +224,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; const loader = function(extent) { loadExtent = extent; - } + }; beforeEach(function() { const layer = new VectorLayer({ @@ -335,7 +335,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; const loader = function(extent) { loadExtent = extent; - } + }; beforeEach(function() { const layer = new VectorLayer({ From 190cd202a177b18c31e29acf69e41c0e3dc1ac46 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Sun, 29 Mar 2020 18:14:31 +0200 Subject: [PATCH 085/119] Always use load extent with real world center --- src/ol/layer/Graticule.js | 3 +- src/ol/renderer/canvas/VectorLayer.js | 7 ++- src/ol/source/Vector.js | 18 ------- .../ol/renderer/canvas/vectorlayer.test.js | 49 ++++++++++++------- 4 files changed, 35 insertions(+), 42 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index aa13cd8fee..15ba7cd2a1 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -437,8 +437,7 @@ class Graticule extends VectorLayer { features: new Collection(), overlaps: false, useSpatialIndex: false, - wrapX: options.wrapX, - loadWrapX: false + wrapX: options.wrapX }) ); diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index bdfe6c2e5b..beef39b2f3 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -361,7 +361,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const center = viewState.center.slice(); const extent = buffer(frameStateExtent, vectorLayerRenderBuffer * resolution); - let loadExtent = extent.slice(); + const loadExtent = extent.slice(); const projectionExtent = viewState.projection.getExtent(); if (vectorSource.getWrapX() && viewState.projection.canWrapX() && @@ -375,11 +375,10 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const gutter = Math.max(getWidth(extent) / 2, worldWidth); extent[0] = projectionExtent[0] - gutter; extent[2] = projectionExtent[2] + gutter; - if (vectorSource.getLoadWrapX()) { - loadExtent = extent; - } const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); center[0] -= (worldsAway * worldWidth); + loadExtent[0] -= (worldsAway * worldWidth); + loadExtent[2] -= (worldsAway * worldWidth); } if (!this.dirty_ && diff --git a/src/ol/source/Vector.js b/src/ol/source/Vector.js index edf1c4e25d..607f0d3b67 100644 --- a/src/ol/source/Vector.js +++ b/src/ol/source/Vector.js @@ -146,10 +146,6 @@ export class VectorSourceEvent extends Event { * @property {boolean} [wrapX=true] Wrap the world horizontally. For vector editing across the * -180° and 180° meridians to work properly, this should be set to `false`. The * resulting geometry coordinates will then exceed the world bounds. - * @property {boolean} [loadWrapX=true] Call the loader with one world width either side - * of the projection extent when the world is wrapped horizontally. This allows features - * to be loaded in a single request, but may be inefficient. If `false` only the viewport - * extent is used and the loader must determine the appropriate real world requests. */ @@ -190,12 +186,6 @@ class VectorSource extends Source { */ this.format_ = options.format; - /** - * @private - * @type {boolean} - */ - this.loadWrapX_ = options.loadWrapX === undefined ? true : options.loadWrapX; - /** * @private * @type {boolean} @@ -811,14 +801,6 @@ class VectorSource extends Source { } - /** - * @return {boolean} The loadWrapX option used to construct the source. - */ - getLoadWrapX() { - return this.loadWrapX_; - } - - /** * @return {boolean} The source can have overlapping geometries. */ diff --git a/test/spec/ol/renderer/canvas/vectorlayer.test.js b/test/spec/ol/renderer/canvas/vectorlayer.test.js index f163a6b4cf..05e7c011b6 100644 --- a/test/spec/ol/renderer/canvas/vectorlayer.test.js +++ b/test/spec/ol/renderer/canvas/vectorlayer.test.js @@ -1,7 +1,7 @@ import Feature from '../../../../../src/ol/Feature.js'; import Map from '../../../../../src/ol/Map.js'; import View from '../../../../../src/ol/View.js'; -import {buffer as bufferExtent, getWidth} from '../../../../../src/ol/extent.js'; +import {buffer as bufferExtent, getWidth, getCenter} from '../../../../../src/ol/extent.js'; import Circle from '../../../../../src/ol/geom/Circle.js'; import Point from '../../../../../src/ol/geom/Point.js'; import {fromExtent} from '../../../../../src/ol/geom/Polygon.js'; @@ -243,7 +243,6 @@ describe('ol.renderer.canvas.VectorLayer', function() { frameState = { viewHints: [], viewState: { - center: [0, 0], projection: projection, resolution: 1, rotation: 0 @@ -251,58 +250,72 @@ describe('ol.renderer.canvas.VectorLayer', function() { }; }); + function setExtent(extent) { + frameState.extent = extent; + frameState.viewState.center = getCenter(extent); + } + it('sets correct extent for small viewport near dateline', function() { - frameState.extent = - [projExtent[0] - 10000, -10000, projExtent[0] + 10000, 10000]; + setExtent([projExtent[0] - 10000, -10000, projExtent[0] + 10000, 10000]); renderer.prepareFrame(frameState); expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); }); it('sets correct extent for viewport less than 1 world wide', function() { - frameState.extent = - [projExtent[0] - 10000, -10000, projExtent[1] - 10000, 10000]; + setExtent([projExtent[0] - 10000, -10000, projExtent[2] - 10000, 10000]); renderer.prepareFrame(frameState); expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); }); it('sets correct extent for viewport more than 1 world wide', function() { - frameState.extent = - [2 * projExtent[0] - 10000, -10000, 2 * projExtent[1] + 10000, 10000]; + setExtent([2 * projExtent[0] + 10000, -10000, 2 * projExtent[2] - 10000, 10000]); renderer.prepareFrame(frameState); expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); + expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); }); - it('sets correct extent for viewport more than 2 worlds wide', function() { + it('sets correct extent for viewport more than 2 worlds wide, one world away', function() { - frameState.extent = [ - projExtent[0] - 2 * worldWidth - 10000, - -10000, projExtent[1] + 2 * worldWidth + 10000, 10000 - ]; + setExtent([projExtent[0] - 2 * worldWidth - 10000, + -10000, projExtent[0] + 2 * worldWidth + 10000, 10000 + ]); renderer.prepareFrame(frameState); expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ projExtent[0] - 2 * worldWidth - 10000, -10000, projExtent[2] + 2 * worldWidth + 10000, 10000 ], buffer)); - expect(loadExtent).to.eql(renderer.replayGroup_.maxExtent_); + const normalizedExtent = [projExtent[0] - 2 * worldWidth + worldWidth - 10000, -10000, projExtent[0] + 2 * worldWidth + worldWidth + 10000, 10000]; + expect(loadExtent).to.eql(bufferExtent(normalizedExtent, buffer)); + }); + + it('sets correct extent for small viewport near dateline, one world away', function() { + + setExtent([-worldWidth - 10000, -10000, -worldWidth + 10000, 10000]); + renderer.prepareFrame(frameState); + expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ + projExtent[0] - worldWidth + buffer, + -10000, projExtent[2] + worldWidth - buffer, 10000 + ], buffer)); + const normalizedExtent = [-10000, -10000, 10000, 10000]; + expect(loadExtent).to.eql(bufferExtent(normalizedExtent, buffer)); }); it('sets replayGroupChanged correctly', function() { - frameState.extent = [-10000, -10000, 10000, 10000]; + setExtent([-10000, -10000, 10000, 10000]); renderer.prepareFrame(frameState); expect(renderer.replayGroupChanged).to.be(true); renderer.prepareFrame(frameState); From 3d8495742bc03775c6d1e4bede168947d9a1f02b Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Sun, 29 Mar 2020 19:50:35 +0100 Subject: [PATCH 086/119] Simplify following renderer changes --- src/ol/layer/Graticule.js | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 15ba7cd2a1..e16cc7d955 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -725,11 +725,7 @@ class Graticule extends VectorLayer { extent[0] = projectionExtent[0]; extent[2] = projectionExtent[2]; } else { - const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); - center[0] -= (worldsAway * worldWidth); - extent[0] -= (worldsAway * worldWidth); - extent[2] -= (worldsAway * worldWidth); - wrapX = !containsExtent(projectionExtent, extent); + wrapX = true; } } From a35794ae973869ea5144c3d822e0a5b3f5642b30 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 30 Mar 2020 12:58:50 +0200 Subject: [PATCH 087/119] Load two extents for views that cross the date line --- src/ol/renderer/canvas/VectorLayer.js | 17 ++- .../ol/renderer/canvas/vectorlayer.test.js | 116 ++++-------------- 2 files changed, 35 insertions(+), 98 deletions(-) diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index beef39b2f3..472333c8c9 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -361,7 +361,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const center = viewState.center.slice(); const extent = buffer(frameStateExtent, vectorLayerRenderBuffer * resolution); - const loadExtent = extent.slice(); + const loadExtents = [extent.slice()]; const projectionExtent = viewState.projection.getExtent(); if (vectorSource.getWrapX() && viewState.projection.canWrapX() && @@ -377,8 +377,15 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { extent[2] = projectionExtent[2] + gutter; const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); center[0] -= (worldsAway * worldWidth); + const loadExtent = loadExtents[0]; loadExtent[0] -= (worldsAway * worldWidth); loadExtent[2] -= (worldsAway * worldWidth); + // If the extent crosses the date line, we load data for both edges of the worlds + if (loadExtent[0] < projectionExtent[0] && loadExtent[2] < projectionExtent[2]) { + loadExtents.push([loadExtent[0] + worldWidth, loadExtent[1], loadExtent[2] + worldWidth, loadExtent[3]]); + } else if (loadExtent[0] > projectionExtent[0] && loadExtent[2] > projectionExtent[2]) { + loadExtents.push([loadExtent[0] - worldWidth, loadExtent[1], loadExtent[2] - worldWidth, loadExtent[3]]); + } } if (!this.dirty_ && @@ -401,10 +408,14 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const userProjection = getUserProjection(); let userTransform; if (userProjection) { - vectorSource.loadFeatures(toUserExtent(loadExtent, projection), resolution, userProjection); + for (let i = 0, ii = loadExtents.length; i < ii; ++i) { + vectorSource.loadFeatures(toUserExtent(loadExtents[i], projection), resolution, userProjection); + } userTransform = getTransformFromProjections(userProjection, projection); } else { - vectorSource.loadFeatures(loadExtent, resolution, projection); + for (let i = 0, ii = loadExtents.length; i < ii; ++i) { + vectorSource.loadFeatures(loadExtents[i], resolution, projection); + } } const squaredTolerance = getSquaredRenderTolerance(resolution, pixelRatio); diff --git a/test/spec/ol/renderer/canvas/vectorlayer.test.js b/test/spec/ol/renderer/canvas/vectorlayer.test.js index 05e7c011b6..f2fabaddd8 100644 --- a/test/spec/ol/renderer/canvas/vectorlayer.test.js +++ b/test/spec/ol/renderer/canvas/vectorlayer.test.js @@ -221,10 +221,11 @@ describe('ol.renderer.canvas.VectorLayer', function() { }); describe('#prepareFrame and #compose', function() { - let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; - const loader = function(extent) { - loadExtent = extent; - }; + let frameState, projExtent, renderer, worldWidth, buffer, loadExtents; + + function loader(extent) { + loadExtents.push(extent); + } beforeEach(function() { const layer = new VectorLayer({ @@ -239,7 +240,7 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent = projection.getExtent(); worldWidth = getWidth(projExtent); buffer = layer.getRenderBuffer(); - loadExtent = undefined; + loadExtents = []; frameState = { viewHints: [], viewState: { @@ -263,7 +264,10 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + expect(loadExtents.length).to.be(2); + expect(loadExtents[0]).to.eql(bufferExtent(frameState.extent, buffer)); + const otherExtent = [projExtent[2] - 10000, -10000, projExtent[2] + 10000, 10000]; + expect(loadExtents[1]).to.eql(bufferExtent(otherExtent, buffer)); }); it('sets correct extent for viewport less than 1 world wide', function() { @@ -274,7 +278,10 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + expect(loadExtents.length).to.be(2); + expect(loadExtents[0]).to.eql(bufferExtent(frameState.extent, buffer)); + const otherExtent = [projExtent[0] - 10000 + worldWidth, -10000, projExtent[2] - 10000 + worldWidth, 10000]; + expect(loadExtents[1]).to.eql(bufferExtent(otherExtent, buffer)); }); it('sets correct extent for viewport more than 1 world wide', function() { @@ -285,7 +292,8 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); + expect(loadExtents.length).to.be(1); + expect(loadExtents[0]).to.eql(bufferExtent(frameState.extent, buffer)); }); it('sets correct extent for viewport more than 2 worlds wide, one world away', function() { @@ -298,11 +306,12 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - 2 * worldWidth - 10000, -10000, projExtent[2] + 2 * worldWidth + 10000, 10000 ], buffer)); + expect(loadExtents.length).to.be(1); const normalizedExtent = [projExtent[0] - 2 * worldWidth + worldWidth - 10000, -10000, projExtent[0] + 2 * worldWidth + worldWidth + 10000, 10000]; - expect(loadExtent).to.eql(bufferExtent(normalizedExtent, buffer)); + expect(loadExtents[0]).to.eql(bufferExtent(normalizedExtent, buffer)); }); - it('sets correct extent for small viewport near dateline, one world away', function() { + it('sets correct extent for small viewport, one world away', function() { setExtent([-worldWidth - 10000, -10000, -worldWidth + 10000, 10000]); renderer.prepareFrame(frameState); @@ -310,8 +319,9 @@ describe('ol.renderer.canvas.VectorLayer', function() { projExtent[0] - worldWidth + buffer, -10000, projExtent[2] + worldWidth - buffer, 10000 ], buffer)); + expect(loadExtents.length).to.be(1); const normalizedExtent = [-10000, -10000, 10000, 10000]; - expect(loadExtent).to.eql(bufferExtent(normalizedExtent, buffer)); + expect(loadExtents[0]).to.eql(bufferExtent(normalizedExtent, buffer)); }); it('sets replayGroupChanged correctly', function() { @@ -344,90 +354,6 @@ describe('ol.renderer.canvas.VectorLayer', function() { }); - describe('#prepareFrame with a loadWrapX: false source', function() { - let frameState, projExtent, renderer, worldWidth, buffer, loadExtent; - const loader = function(extent) { - loadExtent = extent; - }; - - beforeEach(function() { - const layer = new VectorLayer({ - source: new VectorSource({ - wrapX: true, - loadWrapX: false, - loader: loader, - strategy: bboxStrategy - }) - }); - renderer = new CanvasVectorLayerRenderer(layer); - const projection = getProjection('EPSG:3857'); - projExtent = projection.getExtent(); - worldWidth = getWidth(projExtent); - buffer = layer.getRenderBuffer(); - loadExtent = undefined; - frameState = { - viewHints: [], - viewState: { - center: [0, 0], - projection: projection, - resolution: 1, - rotation: 0 - } - }; - }); - - it('loads correct extent for small viewport near dateline', function() { - - frameState.extent = - [projExtent[0] - 10000, -10000, projExtent[0] + 10000, 10000]; - renderer.prepareFrame(frameState); - expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ - projExtent[0] - worldWidth + buffer, - -10000, projExtent[2] + worldWidth - buffer, 10000 - ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); - }); - - it('loads correct extent for viewport less than 1 world wide', function() { - - frameState.extent = - [projExtent[0] - 10000, -10000, projExtent[1] - 10000, 10000]; - renderer.prepareFrame(frameState); - expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ - projExtent[0] - worldWidth + buffer, - -10000, projExtent[2] + worldWidth - buffer, 10000 - ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); - }); - - it('loads correct extent for viewport more than 1 world wide', function() { - - frameState.extent = - [2 * projExtent[0] - 10000, -10000, 2 * projExtent[1] + 10000, 10000]; - renderer.prepareFrame(frameState); - expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ - projExtent[0] - worldWidth + buffer, - -10000, projExtent[2] + worldWidth - buffer, 10000 - ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); - }); - - it('loads correct extent for viewport more than 2 worlds wide', function() { - - frameState.extent = [ - projExtent[0] - 2 * worldWidth - 10000, - -10000, projExtent[1] + 2 * worldWidth + 10000, 10000 - ]; - renderer.prepareFrame(frameState); - expect(renderer.replayGroup_.maxExtent_).to.eql(bufferExtent([ - projExtent[0] - 2 * worldWidth - 10000, - -10000, projExtent[2] + 2 * worldWidth + 10000, 10000 - ], buffer)); - expect(loadExtent).to.eql(bufferExtent(frameState.extent, buffer)); - }); - - }); - describe('hit detection', function() { it('with no fill and transparent fill', function() { From 48b79cf7d1c369d39959c561a61915bc3408e1de Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 14:51:27 +0100 Subject: [PATCH 088/119] only use one extent if two are passed --- src/ol/layer/Graticule.js | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index e16cc7d955..7a991858dc 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -479,11 +479,25 @@ class Graticule extends VectorLayer { * @return {Array} Extents. */ strategyFunction(extent, resolution) { - if (this.loadedExtent_ && !equals(this.loadedExtent_, extent)) { + // extents may be passed in different worlds, to avoid endless loop we use only one + const realExtent = extent.slice(); + if (this.projection_) { + const center = getCenter(extent); + const projectionExtent = this.projection_.getExtent(); + const worldWidth = getWidth(projectionExtent); + if (this.getSource().getWrapX() && this.projection_.canWrapX() && !containsExtent(projectionExtent, extent)) { + const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); + realExtent[0] -= (worldsAway * worldWidth); + realExtent[2] -= (worldsAway * worldWidth); + } + realExtent[0] = Math.round(realExtent[0] * 1e6) / 1e6; + realExtent[2] = Math.round(realExtent[2] * 1e6) / 1e6; + } + if (this.loadedExtent_ && !equals(this.loadedExtent_, realExtent)) { // we should not keep track of loaded extents this.getSource().removeLoadedExtent(this.loadedExtent_); } - return [extent]; + return [realExtent]; } /** From 098885a006244d0c42a4f6683e665a4a07e99ee6 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Mon, 30 Mar 2020 19:26:26 +0200 Subject: [PATCH 089/119] New wrapX functions for coordinate and extent --- src/ol/coordinate.js | 20 +++++++++++++ src/ol/extent.js | 22 ++++++++++++++ src/ol/layer/Graticule.js | 19 ++++-------- src/ol/renderer/Map.js | 14 +++------ src/ol/renderer/canvas/VectorLayer.js | 13 ++++----- src/ol/renderer/canvas/VectorTileLayer.js | 5 ++-- test/spec/ol/coordinate.test.js | 28 +++++++++++++++++- test/spec/ol/extent.test.js | 35 ++++++++++++++++++++++- 8 files changed, 121 insertions(+), 35 deletions(-) diff --git a/src/ol/coordinate.js b/src/ol/coordinate.js index 177c8bce55..fb375162b9 100644 --- a/src/ol/coordinate.js +++ b/src/ol/coordinate.js @@ -3,6 +3,7 @@ */ import {modulo} from './math.js'; import {padNumber} from './string.js'; +import {getWidth} from './extent.js'; /** @@ -402,3 +403,22 @@ export function toStringHDMS(coordinate, opt_fractionDigits) { export function toStringXY(coordinate, opt_fractionDigits) { return format(coordinate, '{x}, {y}', opt_fractionDigits); } + + +/** + * Modifies the provided coordinate in-place to be within the real world + * extent. + * + * @param {Coordinate} coordinate Coordinate. + * @param {import("./proj/Projection.js").default} projection Projection + * @return {Coordinate} The coordinate within the real world extent. + */ +export function wrapX(coordinate, projection) { + const projectionExtent = projection.getExtent(); + if (projection.canWrapX() && (coordinate[0] < projectionExtent[0] || coordinate[0] > projectionExtent[2])) { + const worldWidth = getWidth(projectionExtent); + const worldsAway = Math.floor((coordinate[0] - projectionExtent[0]) / worldWidth); + coordinate[0] -= (worldsAway * worldWidth); + } + return coordinate; +} diff --git a/src/ol/extent.js b/src/ol/extent.js index 94eb9cb249..ef969a196a 100644 --- a/src/ol/extent.js +++ b/src/ol/extent.js @@ -813,3 +813,25 @@ export function applyTransform(extent, transformFn, opt_extent, opt_stops) { } return _boundingExtentXYs(xs, ys, opt_extent); } + + +/** + * Modifies the provided extent in-place to be within the real world + * extent. + * + * @param {Extent} extent Extent. + * @param {import("./proj/Projection.js").default} projection Projection + * @return {Extent} The extent within the real world extent. + */ +export function wrapX(extent, projection) { + const projectionExtent = projection.getExtent(); + const center = getCenter(extent); + if (projection.canWrapX() && (center[0] < projectionExtent[0] || center[0] > projectionExtent[2])) { + const worldWidth = getWidth(projectionExtent); + const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); + const offset = (worldsAway * worldWidth); + extent[0] -= offset; + extent[2] -= offset; + } + return extent; +} diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 7a991858dc..4e4023fd68 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -24,7 +24,9 @@ import { getIntersection, getWidth, intersects, - isEmpty + isEmpty, + buffer as bufferExtent, + wrapX } from '../extent.js'; import {clamp} from '../math.js'; import Style from '../style/Style.js'; @@ -481,19 +483,10 @@ class Graticule extends VectorLayer { strategyFunction(extent, resolution) { // extents may be passed in different worlds, to avoid endless loop we use only one const realExtent = extent.slice(); - if (this.projection_) { - const center = getCenter(extent); - const projectionExtent = this.projection_.getExtent(); - const worldWidth = getWidth(projectionExtent); - if (this.getSource().getWrapX() && this.projection_.canWrapX() && !containsExtent(projectionExtent, extent)) { - const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); - realExtent[0] -= (worldsAway * worldWidth); - realExtent[2] -= (worldsAway * worldWidth); - } - realExtent[0] = Math.round(realExtent[0] * 1e6) / 1e6; - realExtent[2] = Math.round(realExtent[2] * 1e6) / 1e6; + if (this.projection_ && this.getSource().getWrapX()) { + wrapX(realExtent, this.projection_); } - if (this.loadedExtent_ && !equals(this.loadedExtent_, realExtent)) { + if (this.loadedExtent_ && !containsExtent(bufferExtent(this.loadedExtent_, resolution / 2), realExtent)) { // we should not keep track of loaded extents this.getSource().removeLoadedExtent(this.loadedExtent_); } diff --git a/src/ol/renderer/Map.js b/src/ol/renderer/Map.js index 591e96534f..86ee999a81 100644 --- a/src/ol/renderer/Map.js +++ b/src/ol/renderer/Map.js @@ -9,6 +9,7 @@ import {inView} from '../layer/Layer.js'; import {shared as iconImageCache} from '../style/IconImageCache.js'; import {compose as composeTransform, makeInverse} from '../transform.js'; import {renderDeclutterItems} from '../render.js'; +import {wrapX} from '../coordinate.js'; /** * @abstract @@ -102,19 +103,12 @@ class MapRenderer extends Disposable { const projection = viewState.projection; - let translatedCoordinate = coordinate; + const translatedCoordinate = wrapX(coordinate.slice(), projection); const offsets = [[0, 0]]; - if (projection.canWrapX()) { + if (projection.canWrapX() && checkWrapped) { const projectionExtent = projection.getExtent(); const worldWidth = getWidth(projectionExtent); - const x = coordinate[0]; - if (x < projectionExtent[0] || x > projectionExtent[2]) { - const worldsAway = Math.ceil((projectionExtent[0] - x) / worldWidth); - translatedCoordinate = [x + worldWidth * worldsAway, coordinate[1]]; - } - if (checkWrapped) { - offsets.push([-worldWidth, 0], [worldWidth, 0]); - } + offsets.push([-worldWidth, 0], [worldWidth, 0]); } const layerStates = frameState.layerStatesArray; diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index 472333c8c9..0e2bebf908 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -3,7 +3,8 @@ */ import {getUid} from '../../util.js'; import ViewHint from '../../ViewHint.js'; -import {buffer, createEmpty, containsExtent, getWidth, intersects as intersectsExtent} from '../../extent.js'; +import {buffer, createEmpty, containsExtent, getWidth, intersects as intersectsExtent, wrapX as wrapExtentX} from '../../extent.js'; +import {wrapX as wrapCoordinateX} from '../../coordinate.js'; import {fromUserExtent, toUserExtent, getUserProjection, getTransformFromProjections} from '../../proj.js'; import CanvasBuilderGroup from '../../render/canvas/BuilderGroup.js'; import ExecutorGroup, {replayDeclutter} from '../../render/canvas/ExecutorGroup.js'; @@ -364,7 +365,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const loadExtents = [extent.slice()]; const projectionExtent = viewState.projection.getExtent(); - if (vectorSource.getWrapX() && viewState.projection.canWrapX() && + if (vectorSource.getWrapX() && projection.canWrapX() && !containsExtent(projectionExtent, frameState.extent)) { // For the replay group, we need an extent that intersects the real world // (-180° to +180°). To support geometries in a coordinate range from -540° @@ -375,11 +376,9 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const gutter = Math.max(getWidth(extent) / 2, worldWidth); extent[0] = projectionExtent[0] - gutter; extent[2] = projectionExtent[2] + gutter; - const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); - center[0] -= (worldsAway * worldWidth); - const loadExtent = loadExtents[0]; - loadExtent[0] -= (worldsAway * worldWidth); - loadExtent[2] -= (worldsAway * worldWidth); + wrapCoordinateX(center, projection); + const loadExtent = wrapExtentX(loadExtents[0], projection); + wrapExtentX(loadExtent, projection); // If the extent crosses the date line, we load data for both edges of the worlds if (loadExtent[0] < projectionExtent[0] && loadExtent[2] < projectionExtent[2]) { loadExtents.push([loadExtent[0] + worldWidth, loadExtent[1], loadExtent[2] + worldWidth, loadExtent[3]]); diff --git a/src/ol/renderer/canvas/VectorTileLayer.js b/src/ol/renderer/canvas/VectorTileLayer.js index 9c0974fa91..acdd1198d6 100644 --- a/src/ol/renderer/canvas/VectorTileLayer.js +++ b/src/ol/renderer/canvas/VectorTileLayer.js @@ -25,6 +25,7 @@ import { import CanvasExecutorGroup, {replayDeclutter} from '../../render/canvas/ExecutorGroup.js'; import {clear} from '../../obj.js'; import {createHitDetectionImageData, hitDetect} from '../../render/canvas/hitdetect.js'; +import {wrapX} from '../../coordinate.js'; /** @@ -353,9 +354,7 @@ class CanvasVectorTileLayerRenderer extends CanvasTileLayerRenderer { if (tile.getState() === TileState.LOADED && tile.hifi) { const extent = tileGrid.getTileCoordExtent(tile.tileCoord); if (source.getWrapX() && projection.canWrapX() && !containsExtent(projectionExtent, extent)) { - const worldWidth = getWidth(projectionExtent); - const worldsAway = Math.floor((coordinate[0] - projectionExtent[0]) / worldWidth); - coordinate[0] -= (worldsAway * worldWidth); + wrapX(coordinate, projection); } break; } diff --git a/test/spec/ol/coordinate.test.js b/test/spec/ol/coordinate.test.js index 23d18509fc..90b6858718 100644 --- a/test/spec/ol/coordinate.test.js +++ b/test/spec/ol/coordinate.test.js @@ -1,5 +1,6 @@ -import {add as addCoordinate, scale as scaleCoordinate, rotate as rotateCoordinate, equals as coordinatesEqual, format as formatCoordinate, closestOnCircle, closestOnSegment, createStringXY, squaredDistanceToSegment, toStringXY, toStringHDMS} from '../../../src/ol/coordinate.js'; +import {add as addCoordinate, scale as scaleCoordinate, rotate as rotateCoordinate, equals as coordinatesEqual, format as formatCoordinate, closestOnCircle, closestOnSegment, createStringXY, squaredDistanceToSegment, toStringXY, toStringHDMS, wrapX} from '../../../src/ol/coordinate.js'; import Circle from '../../../src/ol/geom/Circle.js'; +import {get} from '../../../src/ol/proj.js'; describe('ol.coordinate', function() { @@ -235,4 +236,29 @@ describe('ol.coordinate', function() { }); }); + describe('wrapX()', function() { + const projection = get('EPSG:4326'); + + it('leaves real world coordinate untouched', function() { + expect(wrapX([16, 48], projection)).to.eql([16, 48]); + }); + + it('moves left world coordinate to real world', function() { + expect(wrapX([-344, 48], projection)).to.eql([16, 48]); + }); + + it('moves right world coordinate to real world', function() { + expect(wrapX([376, 48], projection)).to.eql([16, 48]); + }); + + it('moves far off left coordinate to real world', function() { + expect(wrapX([-1064, 48], projection)).to.eql([16, 48]); + }); + + it('moves far off right coordinate to real world', function() { + expect(wrapX([1096, 48], projection)).to.eql([16, 48]); + }); + + }); + }); diff --git a/test/spec/ol/extent.test.js b/test/spec/ol/extent.test.js index 3e12639d19..2bad7e640a 100644 --- a/test/spec/ol/extent.test.js +++ b/test/spec/ol/extent.test.js @@ -1,5 +1,5 @@ import * as _ol_extent_ from '../../../src/ol/extent.js'; -import {getTransform} from '../../../src/ol/proj.js'; +import {getTransform, get} from '../../../src/ol/proj.js'; import {register} from '../../../src/ol/proj/proj4.js'; @@ -818,4 +818,37 @@ describe('ol.extent', function() { }); + describe('wrapX()', function() { + const projection = get('EPSG:4326'); + + it('leaves real world extent untouched', function() { + expect(_ol_extent_.wrapX([16, 48, 18, 49], projection)).to.eql([16, 48, 18, 49]); + }); + + it('moves left world extent to real world', function() { + expect(_ol_extent_.wrapX([-344, 48, -342, 49], projection)).to.eql([16, 48, 18, 49]); + }); + + it('moves right world extent to real world', function() { + expect(_ol_extent_.wrapX([376, 48, 378, 49], projection)).to.eql([16, 48, 18, 49]); + }); + + it('moves far off left extent to real world', function() { + expect(_ol_extent_.wrapX([-1064, 48, -1062, 49], projection)).to.eql([16, 48, 18, 49]); + }); + + it('moves far off right extent to real world', function() { + expect(_ol_extent_.wrapX([1096, 48, 1098, 49], projection)).to.eql([16, 48, 18, 49]); + }); + + it('leaves -180 crossing extent with real world center untouched', function() { + expect(_ol_extent_.wrapX([-184, 48, 16, 49], projection)).to.eql([-184, 48, 16, 49]); + }); + + it('moves +180 crossing extent with off-world center to the real world', function() { + expect(_ol_extent_.wrapX([300, 48, 376, 49], projection)).to.eql([-60, 48, 16, 49]); + }); + + }); + }); From 660845f5b85a47c4546abe8c2cf54d2be95be912 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 23:17:52 +0100 Subject: [PATCH 090/119] Include center at right edge in calculations --- src/ol/extent.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/extent.js b/src/ol/extent.js index ef969a196a..c68f9c9ff9 100644 --- a/src/ol/extent.js +++ b/src/ol/extent.js @@ -826,7 +826,7 @@ export function applyTransform(extent, transformFn, opt_extent, opt_stops) { export function wrapX(extent, projection) { const projectionExtent = projection.getExtent(); const center = getCenter(extent); - if (projection.canWrapX() && (center[0] < projectionExtent[0] || center[0] > projectionExtent[2])) { + if (projection.canWrapX() && (center[0] < projectionExtent[0] || center[0] >= projectionExtent[2])) { const worldWidth = getWidth(projectionExtent); const worldsAway = Math.floor((center[0] - projectionExtent[0]) / worldWidth); const offset = (worldsAway * worldWidth); From e3ad05f805d06d37df95437337280898b3093d26 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 23:18:52 +0100 Subject: [PATCH 091/119] Include center at right edge in calculations --- src/ol/coordinate.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/coordinate.js b/src/ol/coordinate.js index fb375162b9..79d196a911 100644 --- a/src/ol/coordinate.js +++ b/src/ol/coordinate.js @@ -415,7 +415,7 @@ export function toStringXY(coordinate, opt_fractionDigits) { */ export function wrapX(coordinate, projection) { const projectionExtent = projection.getExtent(); - if (projection.canWrapX() && (coordinate[0] < projectionExtent[0] || coordinate[0] > projectionExtent[2])) { + if (projection.canWrapX() && (coordinate[0] < projectionExtent[0] || coordinate[0] >= projectionExtent[2])) { const worldWidth = getWidth(projectionExtent); const worldsAway = Math.floor((coordinate[0] - projectionExtent[0]) / worldWidth); coordinate[0] -= (worldsAway * worldWidth); From 99a1641afe7296a81d9f86f70cc88e75c4d7cc50 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 23:31:30 +0100 Subject: [PATCH 092/119] remove duplication --- src/ol/renderer/canvas/VectorLayer.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/ol/renderer/canvas/VectorLayer.js b/src/ol/renderer/canvas/VectorLayer.js index 0e2bebf908..0d7af8e81b 100644 --- a/src/ol/renderer/canvas/VectorLayer.js +++ b/src/ol/renderer/canvas/VectorLayer.js @@ -363,7 +363,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { const extent = buffer(frameStateExtent, vectorLayerRenderBuffer * resolution); const loadExtents = [extent.slice()]; - const projectionExtent = viewState.projection.getExtent(); + const projectionExtent = projection.getExtent(); if (vectorSource.getWrapX() && projection.canWrapX() && !containsExtent(projectionExtent, frameState.extent)) { @@ -378,7 +378,6 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer { extent[2] = projectionExtent[2] + gutter; wrapCoordinateX(center, projection); const loadExtent = wrapExtentX(loadExtents[0], projection); - wrapExtentX(loadExtent, projection); // If the extent crosses the date line, we load data for both edges of the worlds if (loadExtent[0] < projectionExtent[0] && loadExtent[2] < projectionExtent[2]) { loadExtents.push([loadExtent[0] + worldWidth, loadExtent[1], loadExtent[2] + worldWidth, loadExtent[3]]); From 6013763480a60af8144915559856653ddb7493a2 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 23:43:26 +0100 Subject: [PATCH 093/119] replace containsExtent with equals in strategy --- src/ol/layer/Graticule.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 4e4023fd68..f66cf5732d 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -25,8 +25,7 @@ import { getWidth, intersects, isEmpty, - buffer as bufferExtent, - wrapX + wrapX as wrapExtentX } from '../extent.js'; import {clamp} from '../math.js'; import Style from '../style/Style.js'; @@ -484,9 +483,11 @@ class Graticule extends VectorLayer { // extents may be passed in different worlds, to avoid endless loop we use only one const realExtent = extent.slice(); if (this.projection_ && this.getSource().getWrapX()) { - wrapX(realExtent, this.projection_); + wrapExtentX(realExtent, this.projection_); } - if (this.loadedExtent_ && !containsExtent(bufferExtent(this.loadedExtent_, resolution / 2), realExtent)) { + realExtent[0] = Math.round(realExtent[0] * 1e8) / 1e8; + realExtent[2] = Math.round(realExtent[2] * 1e8) / 1e8; + if (this.loadedExtent_ && !equals(this.loadedExtent_, realExtent)) { // we should not keep track of loaded extents this.getSource().removeLoadedExtent(this.loadedExtent_); } From 2c7f58dbed352f3025deec869272561b73da974b Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Mon, 30 Mar 2020 23:51:06 +0100 Subject: [PATCH 094/119] remove unused import --- src/ol/renderer/canvas/VectorTileLayer.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/renderer/canvas/VectorTileLayer.js b/src/ol/renderer/canvas/VectorTileLayer.js index acdd1198d6..a3520f9caa 100644 --- a/src/ol/renderer/canvas/VectorTileLayer.js +++ b/src/ol/renderer/canvas/VectorTileLayer.js @@ -6,7 +6,7 @@ import TileState from '../../TileState.js'; import ViewHint from '../../ViewHint.js'; import {listen, unlistenByKey} from '../../events.js'; import EventType from '../../events/EventType.js'; -import {buffer, containsCoordinate, equals, getIntersection, intersects, containsExtent, getWidth, getTopLeft} from '../../extent.js'; +import {buffer, containsCoordinate, equals, getIntersection, intersects, containsExtent, getTopLeft} from '../../extent.js'; import VectorTileRenderType from '../../layer/VectorTileRenderType.js'; import ReplayType from '../../render/canvas/BuilderType.js'; import CanvasBuilderGroup from '../../render/canvas/BuilderGroup.js'; From cdafc4fa05515ceddf0e87d7969c0ff7635f21fe Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Tue, 31 Mar 2020 14:52:02 +0200 Subject: [PATCH 095/119] Add approximatelyEquals function for comparing extents --- src/ol/extent.js | 12 ++++++++++++ src/ol/layer/Graticule.js | 14 ++++++-------- test/spec/ol/extent.test.js | 9 +++++++++ 3 files changed, 27 insertions(+), 8 deletions(-) diff --git a/src/ol/extent.js b/src/ol/extent.js index c68f9c9ff9..4679d49820 100644 --- a/src/ol/extent.js +++ b/src/ol/extent.js @@ -295,6 +295,18 @@ export function equals(extent1, extent2) { extent1[1] == extent2[1] && extent1[3] == extent2[3]; } +/** + * Determine if two extents are approximately equivalent. + * @param {Extent} extent1 Extent 1. + * @param {Extent} extent2 Extent 2. + * @param {number} tolerance Tolerance in extent coordinate units. + * @return {boolean} The two extents differ by less than the tolerance. + */ +export function approximatelyEquals(extent1, extent2, tolerance) { + return Math.abs(extent1[0] - extent2[0]) < tolerance && Math.abs(extent1[2] - extent2[2]) < tolerance && + Math.abs(extent1[1] - extent2[1]) < tolerance && Math.abs(extent1[3] - extent2[3]) < tolerance; +} + /** * Modify an extent to include another extent. diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index f66cf5732d..6fc590283d 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -18,7 +18,7 @@ import { applyTransform, containsCoordinate, containsExtent, - equals, + approximatelyEquals, getCenter, getHeight, getIntersection, @@ -481,17 +481,15 @@ class Graticule extends VectorLayer { */ strategyFunction(extent, resolution) { // extents may be passed in different worlds, to avoid endless loop we use only one - const realExtent = extent.slice(); + const realWorldExtent = extent.slice(); if (this.projection_ && this.getSource().getWrapX()) { - wrapExtentX(realExtent, this.projection_); + wrapExtentX(realWorldExtent, this.projection_); } - realExtent[0] = Math.round(realExtent[0] * 1e8) / 1e8; - realExtent[2] = Math.round(realExtent[2] * 1e8) / 1e8; - if (this.loadedExtent_ && !equals(this.loadedExtent_, realExtent)) { + if (this.loadedExtent_ && !approximatelyEquals(this.loadedExtent_, realWorldExtent, resolution)) { // we should not keep track of loaded extents this.getSource().removeLoadedExtent(this.loadedExtent_); } - return [realExtent]; + return [realWorldExtent]; } /** @@ -508,7 +506,7 @@ class Graticule extends VectorLayer { const layerExtent = this.getExtent() || [-Infinity, -Infinity, Infinity, Infinity]; const renderExtent = getIntersection(layerExtent, extent); - if (this.renderedExtent_ && equals(this.renderedExtent_, renderExtent)) { + if (this.renderedExtent_ && approximatelyEquals(this.renderedExtent_, renderExtent, resolution)) { return; } this.renderedExtent_ = renderExtent; diff --git a/test/spec/ol/extent.test.js b/test/spec/ol/extent.test.js index 2bad7e640a..ba971781da 100644 --- a/test/spec/ol/extent.test.js +++ b/test/spec/ol/extent.test.js @@ -851,4 +851,13 @@ describe('ol.extent', function() { }); + describe('approximatelyEquals', function() { + it('returns true when within tolerance', function() { + expect(_ol_extent_.approximatelyEquals([16, 48, 17, 49], [16.09, 48, 17, 49], 0.1)).to.be(true); + }); + it('returns false when not within tolerance', function() { + expect(_ol_extent_.approximatelyEquals([16, 48, 17, 49], [16.11, 48, 17, 49], 0.1)).to.be(false); + }); + }); + }); From 9af1e223afc38a8bc0c93b0f48c42afcb1cc2406 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Tue, 31 Mar 2020 15:52:29 +0200 Subject: [PATCH 096/119] More tests and docs for extent and coordinate wrapX --- src/ol/coordinate.js | 3 ++- test/spec/ol/extent.test.js | 6 ++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/ol/coordinate.js b/src/ol/coordinate.js index 79d196a911..563ff1bf64 100644 --- a/src/ol/coordinate.js +++ b/src/ol/coordinate.js @@ -407,7 +407,8 @@ export function toStringXY(coordinate, opt_fractionDigits) { /** * Modifies the provided coordinate in-place to be within the real world - * extent. + * extent. The lower projection extent boundary is inclusive, the upper one + * exclusive. * * @param {Coordinate} coordinate Coordinate. * @param {import("./proj/Projection.js").default} projection Projection diff --git a/test/spec/ol/extent.test.js b/test/spec/ol/extent.test.js index ba971781da..cc9011175a 100644 --- a/test/spec/ol/extent.test.js +++ b/test/spec/ol/extent.test.js @@ -849,6 +849,12 @@ describe('ol.extent', function() { expect(_ol_extent_.wrapX([300, 48, 376, 49], projection)).to.eql([-60, 48, 16, 49]); }); + it('produces the same real world extent for shifted extents with center at +/-180', function() { + expect(_ol_extent_.wrapX([360, -90, 720, 90], projection)).to.eql([-360, -90, 0, 90]); + expect(_ol_extent_.wrapX([0, -90, 360, 90], projection)).to.eql([-360, -90, 0, 90]); + expect(_ol_extent_.wrapX([-360, -90, 0, 90], projection)).to.eql([-360, -90, 0, 90]); + }); + }); describe('approximatelyEquals', function() { From 149ca7efad89d185344e876a0bc485e65e5c1b33 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 16:26:30 +0100 Subject: [PATCH 097/119] return previous extent if extents are approx equal --- src/ol/layer/Graticule.js | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 6fc590283d..3994cd11a1 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -481,13 +481,18 @@ class Graticule extends VectorLayer { */ strategyFunction(extent, resolution) { // extents may be passed in different worlds, to avoid endless loop we use only one - const realWorldExtent = extent.slice(); + let realWorldExtent = extent.slice(); if (this.projection_ && this.getSource().getWrapX()) { wrapExtentX(realWorldExtent, this.projection_); } - if (this.loadedExtent_ && !approximatelyEquals(this.loadedExtent_, realWorldExtent, resolution)) { - // we should not keep track of loaded extents - this.getSource().removeLoadedExtent(this.loadedExtent_); + if (this.loadedExtent_) { + if (approximatelyEquals(this.loadedExtent_, realWorldExtent, resolution)) { + // make sure result is exactly equal to previous extent + realWorldExtent = this.loadedExtent_.slice(); + } else { + // we should not keep track of loaded extents + this.getSource().removeLoadedExtent(this.loadedExtent_); + } } return [realWorldExtent]; } From 929b9f4068ee576e0902a794053c94cae19b818f Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 16:55:23 +0100 Subject: [PATCH 098/119] change loader check back to equal extents --- src/ol/layer/Graticule.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 3994cd11a1..691637b6ae 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -18,6 +18,7 @@ import { applyTransform, containsCoordinate, containsExtent, + equals, approximatelyEquals, getCenter, getHeight, @@ -511,7 +512,7 @@ class Graticule extends VectorLayer { const layerExtent = this.getExtent() || [-Infinity, -Infinity, Infinity, Infinity]; const renderExtent = getIntersection(layerExtent, extent); - if (this.renderedExtent_ && approximatelyEquals(this.renderedExtent_, renderExtent, resolution)) { + if (this.renderedExtent_ && equals(this.renderedExtent_, renderExtent, resolution)) { return; } this.renderedExtent_ = renderExtent; From bfca3cf713e50ab3784f7889209daefe2865e711 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 17:00:12 +0100 Subject: [PATCH 099/119] change loader check back to equal extents --- src/ol/layer/Graticule.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ol/layer/Graticule.js b/src/ol/layer/Graticule.js index 691637b6ae..6051a608aa 100644 --- a/src/ol/layer/Graticule.js +++ b/src/ol/layer/Graticule.js @@ -512,7 +512,7 @@ class Graticule extends VectorLayer { const layerExtent = this.getExtent() || [-Infinity, -Infinity, Infinity, Infinity]; const renderExtent = getIntersection(layerExtent, extent); - if (this.renderedExtent_ && equals(this.renderedExtent_, renderExtent, resolution)) { + if (this.renderedExtent_ && equals(this.renderedExtent_, renderExtent)) { return; } this.renderedExtent_ = renderExtent; From 3c0ff154145a9e54b3d0470d50d696184eec949c Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 22:32:02 +0100 Subject: [PATCH 100/119] Cap Longitudes and replace Bing with MapTiler --- examples/vector-osm.js | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/examples/vector-osm.js b/examples/vector-osm.js index 83d504b7d6..96cd3dde4a 100644 --- a/examples/vector-osm.js +++ b/examples/vector-osm.js @@ -85,8 +85,8 @@ const vectorSource = new VectorSource({ vectorSource.addFeatures(features); }); const query = '(node(' + - epsg4326Extent[1] + ',' + epsg4326Extent[0] + ',' + - epsg4326Extent[3] + ',' + epsg4326Extent[2] + + epsg4326Extent[1] + ',' + Math.max(epsg4326Extent[0], -180) + ',' + + epsg4326Extent[3] + ',' + Math.min(epsg4326Extent[2], 180) + ');rel(bn)->.foo;way(bn);node(w)->.foo;rel(bw););out meta;'; client.send(query); }, @@ -110,10 +110,15 @@ const vector = new VectorLayer({ } }); +const key = 'get_your_own_D6rA4zTHduk6KOKTXzGB'; +const attributions = '© MapTiler ' + + '© OpenStreetMap contributors'; + const raster = new TileLayer({ - source: new BingMaps({ - imagerySet: 'Aerial', - key: 'As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5' + source: new XYZ({ + attributions: attributions, + url: 'https://api.maptiler.com/tiles/satellite/{z}/{x}/{y}.jpg?key=' + key, + maxZoom: 20 }) }); From 7b55fe381eb3f6d60ccb6af6ae52aa99eb27ce97 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 22:36:07 +0100 Subject: [PATCH 101/119] Replace Bing layer with MapTiler --- examples/vector-osm.html | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/examples/vector-osm.html b/examples/vector-osm.html index c8e19ea2c0..0bdaf67045 100644 --- a/examples/vector-osm.html +++ b/examples/vector-osm.html @@ -4,9 +4,9 @@ title: OSM XML shortdesc: Example of using the OSM XML source. docs: > OSM XML vector data is loaded dynamically from a the [Overpass API](http://overpass-api.de) using a bbox strategy. Note that panning and zooming will eventually lead to "Too many requests" errors from the Overpass API. -tags: "vector, osmxml, loading, server, strategy, bbox" +tags: "vector, osmxml, loading, server, strategy, bbox, maptiler" cloak: - - key: As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5 - value: Your Bing Maps Key from http://www.bingmapsportal.com/ here + - key: get_your_own_D6rA4zTHduk6KOKTXzGB + value: Get your own API key at https://www.maptiler.com/cloud/ ---
    From 82dd764d13801052d75b4b1e68cb043d814b83f7 Mon Sep 17 00:00:00 2001 From: mike-000 <49240900+mike-000@users.noreply.github.com> Date: Tue, 31 Mar 2020 22:37:51 +0100 Subject: [PATCH 102/119] Replace Bing layer with MapTiler --- examples/vector-osm.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/vector-osm.js b/examples/vector-osm.js index 96cd3dde4a..d67d520205 100644 --- a/examples/vector-osm.js +++ b/examples/vector-osm.js @@ -4,7 +4,7 @@ import OSMXML from '../src/ol/format/OSMXML.js'; import {Tile as TileLayer, Vector as VectorLayer} from '../src/ol/layer.js'; import {bbox as bboxStrategy} from '../src/ol/loadingstrategy.js'; import {transformExtent} from '../src/ol/proj.js'; -import BingMaps from '../src/ol/source/BingMaps.js'; +import XYZ from '../src/ol/source/XYZ.js'; import VectorSource from '../src/ol/source/Vector.js'; import {Circle as CircleStyle, Fill, Stroke, Style} from '../src/ol/style.js'; From 2b863793d0ba70d570966bb6436cbd9b2e43a5a4 Mon Sep 17 00:00:00 2001 From: Edward Nash Date: Wed, 1 Apr 2020 06:50:01 +0200 Subject: [PATCH 103/119] Perform auto-pan when adding an Overlay to a Map * Auto-pan settings currently only activate when the position of the Overlay is set and the Overlay is already on a Map. * The consequence of this is that creating an Overlay with position set and then adding to a Map results in no auto-pan being performed - it is necessary to first create the Overlay, then add to a Map and finally set the position in order for the Map to auto-pan. * This commit changes this behaviour so that the auto-pan settings are also considered when the map property of the Overlay is set and not only when the position property is set, leading to a more intuitive behaviour. * Fixes Issue #10843 --- src/ol/Overlay.js | 1 + 1 file changed, 1 insertion(+) diff --git a/src/ol/Overlay.js b/src/ol/Overlay.js index b0025d08d8..c99aea8452 100644 --- a/src/ol/Overlay.js +++ b/src/ol/Overlay.js @@ -300,6 +300,7 @@ class Overlay extends BaseObject { } else { container.appendChild(this.element); } + this.performAutoPan(); } } From 061ccb987b2fbdd14e888fd088392a78b603ed34 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 1 Apr 2020 08:43:30 +0200 Subject: [PATCH 104/119] Key update --- examples/bing-maps.html | 2 +- examples/bing-maps.js | 2 +- examples/mobile-full-screen.html | 2 +- examples/mobile-full-screen.js | 2 +- examples/preload.html | 2 +- examples/preload.js | 4 ++-- 6 files changed, 7 insertions(+), 7 deletions(-) diff --git a/examples/bing-maps.html b/examples/bing-maps.html index a3e7b5b48f..b03cf180f0 100644 --- a/examples/bing-maps.html +++ b/examples/bing-maps.html @@ -6,7 +6,7 @@ docs: >

    When the Bing Maps tile service doesn't have tiles for a given resolution and region it returns "placeholder" tiles indicating that. Zoom the map beyond level 19 to see the "placeholder" tiles. If you want OpenLayers to display stretched tiles in place of "placeholder" tiles beyond zoom level 19 then set maxZoom to 19 in the options passed to ol/source/BingMaps.

    tags: "bing, bing-maps" cloak: - - key: As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5 + - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd value: Your Bing Maps Key from http://www.bingmapsportal.com/ here ---
    diff --git a/examples/bing-maps.js b/examples/bing-maps.js index b0ecb7c2be..eabdcae542 100644 --- a/examples/bing-maps.js +++ b/examples/bing-maps.js @@ -18,7 +18,7 @@ for (i = 0, ii = styles.length; i < ii; ++i) { visible: false, preload: Infinity, source: new BingMaps({ - key: 'As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5', + key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', imagerySet: styles[i] // use maxZoom 19 to see stretched tiles instead of the BingMaps // "no photos at this zoom level" tiles diff --git a/examples/mobile-full-screen.html b/examples/mobile-full-screen.html index 8bb8b0ee22..05915d0280 100644 --- a/examples/mobile-full-screen.html +++ b/examples/mobile-full-screen.html @@ -4,7 +4,7 @@ title: Full-Screen Mobile shortdesc: Example of a full screen map. tags: "fullscreen, geolocation, mobile" cloak: - - key: As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5 + - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd value: Your Bing Maps Key from http://www.bingmapsportal.com/ here --- diff --git a/examples/mobile-full-screen.js b/examples/mobile-full-screen.js index d1a3071bbe..65535f6a50 100644 --- a/examples/mobile-full-screen.js +++ b/examples/mobile-full-screen.js @@ -14,7 +14,7 @@ const map = new Map({ layers: [ new TileLayer({ source: new BingMaps({ - key: 'As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5', + key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', imagerySet: 'RoadOnDemand' }) }) diff --git a/examples/preload.html b/examples/preload.html index 7398986e0b..87ca0b1304 100644 --- a/examples/preload.html +++ b/examples/preload.html @@ -6,7 +6,7 @@ docs: >

    The map on the top preloads low resolution tiles. The map on the bottom does not use any preloading. Try zooming out and panning to see the difference.

    tags: "preload, bing" cloak: - - key: As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5 + - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd value: Your Bing Maps Key from http://www.bingmapsportal.com/ here ---
    diff --git a/examples/preload.js b/examples/preload.js index 5d15402941..8107ed267f 100644 --- a/examples/preload.js +++ b/examples/preload.js @@ -14,7 +14,7 @@ const map1 = new Map({ new TileLayer({ preload: Infinity, source: new BingMaps({ - key: 'As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5', + key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', imagerySet: 'Aerial' }) }) @@ -28,7 +28,7 @@ const map2 = new Map({ new TileLayer({ preload: 0, // default value source: new BingMaps({ - key: 'As1HiMj1PvLPlqc_gtM7AqZfBL8ZL3VrjaS3zIb22Uvb9WKhuJObROC-qUpa81U5', + key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', imagerySet: 'AerialWithLabelsOnDemand' }) }) From 7dd42ef19fa61f7b935d248dcd25655a72cc161a Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Wed, 1 Apr 2020 09:07:07 +0200 Subject: [PATCH 105/119] Key update --- examples/bing-maps.html | 2 +- examples/bing-maps.js | 2 +- examples/mobile-full-screen.html | 2 +- examples/mobile-full-screen.js | 2 +- examples/preload.html | 2 +- examples/preload.js | 4 ++-- 6 files changed, 7 insertions(+), 7 deletions(-) diff --git a/examples/bing-maps.html b/examples/bing-maps.html index b03cf180f0..e201f69efc 100644 --- a/examples/bing-maps.html +++ b/examples/bing-maps.html @@ -6,7 +6,7 @@ docs: >

    When the Bing Maps tile service doesn't have tiles for a given resolution and region it returns "placeholder" tiles indicating that. Zoom the map beyond level 19 to see the "placeholder" tiles. If you want OpenLayers to display stretched tiles in place of "placeholder" tiles beyond zoom level 19 then set maxZoom to 19 in the options passed to ol/source/BingMaps.

    tags: "bing, bing-maps" cloak: - - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd + - key: ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp value: Your Bing Maps Key from http://www.bingmapsportal.com/ here ---
    diff --git a/examples/bing-maps.js b/examples/bing-maps.js index eabdcae542..1823ab4740 100644 --- a/examples/bing-maps.js +++ b/examples/bing-maps.js @@ -18,7 +18,7 @@ for (i = 0, ii = styles.length; i < ii; ++i) { visible: false, preload: Infinity, source: new BingMaps({ - key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', + key: 'ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp ', imagerySet: styles[i] // use maxZoom 19 to see stretched tiles instead of the BingMaps // "no photos at this zoom level" tiles diff --git a/examples/mobile-full-screen.html b/examples/mobile-full-screen.html index 05915d0280..cfc4a270c1 100644 --- a/examples/mobile-full-screen.html +++ b/examples/mobile-full-screen.html @@ -4,7 +4,7 @@ title: Full-Screen Mobile shortdesc: Example of a full screen map. tags: "fullscreen, geolocation, mobile" cloak: - - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd + - key: ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp value: Your Bing Maps Key from http://www.bingmapsportal.com/ here --- diff --git a/examples/mobile-full-screen.js b/examples/mobile-full-screen.js index 65535f6a50..80d03d2a5f 100644 --- a/examples/mobile-full-screen.js +++ b/examples/mobile-full-screen.js @@ -14,7 +14,7 @@ const map = new Map({ layers: [ new TileLayer({ source: new BingMaps({ - key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', + key: 'ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp ', imagerySet: 'RoadOnDemand' }) }) diff --git a/examples/preload.html b/examples/preload.html index 87ca0b1304..e13138d2aa 100644 --- a/examples/preload.html +++ b/examples/preload.html @@ -6,7 +6,7 @@ docs: >

    The map on the top preloads low resolution tiles. The map on the bottom does not use any preloading. Try zooming out and panning to see the difference.

    tags: "preload, bing" cloak: - - key: Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd + - key: ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp value: Your Bing Maps Key from http://www.bingmapsportal.com/ here ---
    diff --git a/examples/preload.js b/examples/preload.js index 8107ed267f..6bf91a82ad 100644 --- a/examples/preload.js +++ b/examples/preload.js @@ -14,7 +14,7 @@ const map1 = new Map({ new TileLayer({ preload: Infinity, source: new BingMaps({ - key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', + key: 'ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp ', imagerySet: 'Aerial' }) }) @@ -28,7 +28,7 @@ const map2 = new Map({ new TileLayer({ preload: 0, // default value source: new BingMaps({ - key: 'Avgbq4irmuveuESSXWk_LNBp5HFobQx8QgHDA4gWEQo2OqYHrYqCF0WL6-_TbrTd', + key: 'ApTJzdkyN1DdFKkRAE6QIDtzihNaf6IWJsT-nQ_2eMoO4PN__0Tzhl2-WgJtXFSp ', imagerySet: 'AerialWithLabelsOnDemand' }) }) From 23c2e1062ca57cef829582eef11e1ad804152468 Mon Sep 17 00:00:00 2001 From: Simon Daron Date: Wed, 1 Apr 2020 10:08:37 +0200 Subject: [PATCH 106/119] Add an example of clipping layer based on a vector source --- examples/layer-clipping-vector.css | 3 ++ examples/layer-clipping-vector.html | 9 ++++++ examples/layer-clipping-vector.js | 46 +++++++++++++++++++++++++++++ 3 files changed, 58 insertions(+) create mode 100644 examples/layer-clipping-vector.css create mode 100644 examples/layer-clipping-vector.html create mode 100644 examples/layer-clipping-vector.js diff --git a/examples/layer-clipping-vector.css b/examples/layer-clipping-vector.css new file mode 100644 index 0000000000..3d35756e41 --- /dev/null +++ b/examples/layer-clipping-vector.css @@ -0,0 +1,3 @@ +#map { + background: transparent; +} diff --git a/examples/layer-clipping-vector.html b/examples/layer-clipping-vector.html new file mode 100644 index 0000000000..2343aa0105 --- /dev/null +++ b/examples/layer-clipping-vector.html @@ -0,0 +1,9 @@ +--- +layout: example.html +title: Vector Clipping Layer +shortdesc: Vector Clipping Layer example +docs: > + Example of a clipping layer based on a vector source +tags: "clipping, openstreetmap, vector" +--- +
    diff --git a/examples/layer-clipping-vector.js b/examples/layer-clipping-vector.js new file mode 100644 index 0000000000..13c416b477 --- /dev/null +++ b/examples/layer-clipping-vector.js @@ -0,0 +1,46 @@ +import Map from '../src/ol/Map.js'; +import View from '../src/ol/View.js'; +import {Tile as TileLayer, Vector as VectorLayer} from '../src/ol/layer.js'; +import VectorSource from '../src/ol/source/Vector.js'; +import GeoJSON from '../src/ol/format/GeoJSON.js'; +import OSM from '../src/ol/source/OSM.js'; +import {Fill, Style} from '../src/ol/style.js'; +import {getVectorContext} from '../src/ol/render.js'; +import {fromLonLat} from '../src/ol/proj.js'; + +const base = new TileLayer({ + source: new OSM() +}); + +const clipLayer = new VectorLayer({ + style: null, + source: new VectorSource({ + url: + './data/geojson/switzerland.geojson', + format: new GeoJSON() + }) +}); + +const style = new Style({ + fill: new Fill({ + color: 'black' + }) +}); + +base.on('postrender', function(e) { + e.context.globalCompositeOperation = 'destination-in'; + const vectorContext = getVectorContext(e); + clipLayer.getSource().forEachFeature(function(feature) { + vectorContext.drawFeature(feature, style); + }); + e.context.globalCompositeOperation = 'source-over'; +}); + +const map = new Map({ + layers: [base, clipLayer], + target: 'map', + view: new View({ + center: fromLonLat([8.23, 46.86]), + zoom: 7 + }) +}); From 8e6b5ce0bf994a1fb69712e5d6a3f4f0bf4d3019 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Thu, 2 Apr 2020 13:50:12 +0200 Subject: [PATCH 107/119] Update dependencies --- package-lock.json | 53 +++++++++++++++++++++++++++-------------------- package.json | 6 +++--- 2 files changed, 33 insertions(+), 26 deletions(-) diff --git a/package-lock.json b/package-lock.json index 9e29ee74e7..a4173b921a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5971,8 +5971,7 @@ "dependencies": { "minimist": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "resolved": "", "dev": true, "optional": true } @@ -6326,15 +6325,15 @@ "dev": true }, "handlebars": { - "version": "4.7.3", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.3.tgz", - "integrity": "sha512-SRGwSYuNfx8DwHD/6InAPzD6RgeruWLT+B8e8a7gGs8FWgHzlExpTFMEq2IA6QpAfOClpKHy6+8IqTjeBCu6Kg==", + "version": "4.7.4", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.4.tgz", + "integrity": "sha512-Is8+SzHv8K9STNadlBVpVhxXrSXxVgTyIvhdg2Qjak1SfSZ7iEozLHdwiX1jJ9lLFkcFJxqGK5s/cI7ZX+qGkQ==", "dev": true, "requires": { "neo-async": "^2.6.0", - "optimist": "^0.6.1", "source-map": "^0.6.1", - "uglify-js": "^3.1.4" + "uglify-js": "^3.1.4", + "yargs": "^15.3.1" } }, "har-schema": { @@ -7730,6 +7729,14 @@ "dev": true, "requires": { "minimist": "1.2.0" + }, + "dependencies": { + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true + } } }, "karma-sourcemap-loader": { @@ -7801,9 +7808,9 @@ "dev": true }, "kind-of": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", - "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", + "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==", "dev": true }, "klaw": { @@ -8217,9 +8224,9 @@ } }, "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", "dev": true }, "minipass": { @@ -9515,13 +9522,13 @@ "dev": true }, "proj4": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/proj4/-/proj4-2.6.0.tgz", - "integrity": "sha512-ll2WyehUFOyzEZtN8hAiOTmZpuDCN5V+4A/HjhPbhlwVwlsFKnIHSZ3l3uhzgDndHjoL2MyERFGe9VmXN4rYUg==", + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/proj4/-/proj4-2.6.1.tgz", + "integrity": "sha512-RP5EcrfrLcARy+Zjjz1wIeqZzZdPtQNl685asHcwdU/MQ/dvydmf1XWM4mgok6wPaNsXZ8IFrM4qadO3g46PiQ==", "dev": true, "requires": { "mgrs": "1.0.0", - "wkt-parser": "^1.2.0" + "wkt-parser": "^1.2.4" } }, "promise-inflight": { @@ -11927,9 +11934,9 @@ "dev": true }, "uglify-js": { - "version": "3.7.7", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.7.7.tgz", - "integrity": "sha512-FeSU+hi7ULYy6mn8PKio/tXsdSXN35lm4KgV2asx00kzrLU9Pi3oAslcJT70Jdj7PHX29gGUPOT6+lXGBbemhA==", + "version": "3.8.1", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.8.1.tgz", + "integrity": "sha512-W7KxyzeaQmZvUFbGj4+YFshhVrMBGSg2IbcYAjGWGvx8DHvJMclbTDMpffdxFUGPBHjIytk7KJUR/KUXstUGDw==", "dev": true, "optional": true, "requires": { @@ -12681,9 +12688,9 @@ } }, "wkt-parser": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/wkt-parser/-/wkt-parser-1.2.3.tgz", - "integrity": "sha512-s7zrOedGuHbbzMaQOuf8HacuCYp3LmmrHjkkN//7UEAzsYz7xJ6J+j/84ZWZkQcrRqi3xXyuc4odPHj7PEB0bw==", + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/wkt-parser/-/wkt-parser-1.2.4.tgz", + "integrity": "sha512-ZzKnc7ml/91fOPh5bANBL4vUlWPIYYv11waCtWTkl2TRN+LEmBg60Q1MA8gqV4hEp4MGfSj9JiHz91zw/gTDXg==", "dev": true }, "word-wrap": { diff --git a/package.json b/package.json index 7d6c715384..1bb076716b 100644 --- a/package.json +++ b/package.json @@ -67,7 +67,7 @@ "fs-extra": "^9.0.0", "glob": "^7.1.5", "globby": "^11.0.0", - "handlebars": "4.7.3", + "handlebars": "4.7.4", "istanbul": "0.4.5", "istanbul-instrumenter-loader": "^3.0.1", "jquery": "3.4.1", @@ -84,10 +84,10 @@ "loglevelnext": "^3.0.1", "marked": "0.8.2", "mocha": "7.1.1", - "ol-mapbox-style": "^6.1.0", + "ol-mapbox-style": "^6.1.1", "pixelmatch": "^5.1.0", "pngjs": "^3.4.0", - "proj4": "2.6.0", + "proj4": "2.6.1", "puppeteer": "~2.1.0", "rollup": "^2.1.0", "rollup-plugin-babel": "^4.3.3", From 72907566bbbb6f760e2fb7be02d22766ecf191cd Mon Sep 17 00:00:00 2001 From: philip Date: Thu, 2 Apr 2020 14:14:13 +0000 Subject: [PATCH 108/119] Add comment to explain calculation. --- src/ol/reproj/Triangulation.js | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/ol/reproj/Triangulation.js b/src/ol/reproj/Triangulation.js index b6091d149f..ba49bac8c4 100644 --- a/src/ol/reproj/Triangulation.js +++ b/src/ol/reproj/Triangulation.js @@ -139,6 +139,16 @@ class Triangulation { const sourceBottomRight = this.transformInv_(destinationBottomRight); const sourceBottomLeft = this.transformInv_(destinationBottomLeft); + /* + * The maxSubdivision controls how many splittings of the target area can + * be done. The idea here is to do a linear mapping of the target areas + * but the actual overal reprojection (can be) extremely non-linear. The + * default value of MAX_SUBDIVISION was chosen based on mapping a 256x256 + * tile size. However this function is also called to remap canvas rendered + * layers which can be much larger. This calculation increases the maxSubdivision + * value by the right factor so that each 256x256 pixel area has + * MAX_SUBDIVISION divisions. + */ const maxSubdivision = MAX_SUBDIVISION + (opt_destinationResolution ? Math.max(0, Math.ceil(Math.log2(getArea(targetExtent) / (opt_destinationResolution * opt_destinationResolution * 256 * 256)))) From 10c7f08fa41ae2efb4217006ef68161ce3277962 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Tue, 7 Jan 2020 11:28:19 +0100 Subject: [PATCH 109/119] Select style multiple select interactions removed This fixes issue 10486 by removing the event listeners when an interaction is removed from a map. --- src/ol/interaction/Select.js | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/src/ol/interaction/Select.js b/src/ol/interaction/Select.js index 11a3c74bd0..3bd762db51 100644 --- a/src/ol/interaction/Select.js +++ b/src/ol/interaction/Select.js @@ -167,6 +167,16 @@ class Select extends Interaction { const options = opt_options ? opt_options : {}; + /** + * @private + */ + this.boundAddFeature_ = this.addFeature_.bind(this); + + /** + * @private + */ + this.boundRemoveFeature_ = this.removeFeature_.bind(this); + /** * @private * @type {import("../events/condition.js").Condition} @@ -250,9 +260,8 @@ class Select extends Interaction { */ this.featureLayerAssociation_ = {}; - const features = this.getFeatures(); - features.addEventListener(CollectionEventType.ADD, this.addFeature_.bind(this)); - features.addEventListener(CollectionEventType.REMOVE, this.removeFeature_.bind(this)); + this.features_.addEventListener(CollectionEventType.ADD, this.boundAddFeature_); + this.features_.addEventListener(CollectionEventType.REMOVE, this.boundRemoveFeature_); } /** @@ -323,6 +332,10 @@ class Select extends Interaction { if (map && this.style_) { this.features_.forEach(this.applySelectedStyle_.bind(this)); } + if (!map) { + this.features_.removeEventListener(CollectionEventType.ADD, this.boundAddFeature_); + this.features_.removeEventListener(CollectionEventType.REMOVE, this.boundRemoveFeature_); + } } /** From a30a92a9635e40f99e4c19270c58ab0c2cc9abab Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 10:53:00 +0100 Subject: [PATCH 110/119] CK-240: fix multiple select interactions on map event handlers have to be (de)activated when the interaction is added or removed to the map, not when constructed added unit test --- src/ol/interaction/Select.js | 12 +++--- test/spec/ol/interaction/select.test.js | 50 +++++++++++++++++++++++++ 2 files changed, 57 insertions(+), 5 deletions(-) diff --git a/src/ol/interaction/Select.js b/src/ol/interaction/Select.js index 3bd762db51..a08c22bc54 100644 --- a/src/ol/interaction/Select.js +++ b/src/ol/interaction/Select.js @@ -259,9 +259,6 @@ class Select extends Interaction { * @type {Object} */ this.featureLayerAssociation_ = {}; - - this.features_.addEventListener(CollectionEventType.ADD, this.boundAddFeature_); - this.features_.addEventListener(CollectionEventType.REMOVE, this.boundRemoveFeature_); } /** @@ -329,8 +326,13 @@ class Select extends Interaction { this.features_.forEach(this.restorePreviousStyle_.bind(this)); } super.setMap(map); - if (map && this.style_) { - this.features_.forEach(this.applySelectedStyle_.bind(this)); + if (map) { + this.features_.addEventListener(CollectionEventType.ADD, this.boundAddFeature_); + this.features_.addEventListener(CollectionEventType.REMOVE, this.boundRemoveFeature_); + + if (this.style_) { + this.features_.forEach(this.applySelectedStyle_.bind(this)); + } } if (!map) { this.features_.removeEventListener(CollectionEventType.ADD, this.boundAddFeature_); diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index e64eb2dc28..65d47cea43 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -9,6 +9,7 @@ import Interaction from '../../../../src/ol/interaction/Interaction.js'; import Select from '../../../../src/ol/interaction/Select.js'; import VectorLayer from '../../../../src/ol/layer/Vector.js'; import VectorSource from '../../../../src/ol/source/Vector.js'; +import Style from '../../../../src/ol/style/Style.js'; describe('ol.interaction.Select', function() { @@ -406,4 +407,53 @@ describe('ol.interaction.Select', function() { }); }); + + describe('clear event listeners on interaction removal', function() { + let firstInteraction, secondInteraction, feature; + + beforeEach(function() { + feature = source.getFeatures()[3]; // top feature is selected + + const style = new Style({}); + const features = new Collection(); + + firstInteraction = new Select({ style, features }); + secondInteraction = new Select({ style, features }); + }); + + afterEach(function() { + map.removeInteraction(secondInteraction); + map.removeInteraction(firstInteraction); + }); + + // The base case + describe('with a single interaction added', function() { + it('changes the selected feature once', function() { + map.addInteraction(firstInteraction); + + const listenerSpy = sinon.spy(); + feature.on('change', listenerSpy); + + simulateEvent('singleclick', 10, -20, false); + + expect(listenerSpy.callCount).to.be(1); + }); + }); + + // The "difficult" case. To prevent regression + describe('with a replaced interaction', function() { + it('changes the selected feature once', function() { + map.addInteraction(firstInteraction); + map.removeInteraction(firstInteraction); + map.addInteraction(secondInteraction); + + const listenerSpy = sinon.spy(); + feature.on('change', listenerSpy); + + simulateEvent('singleclick', 10, -20, false); + + expect(listenerSpy.callCount).to.be(1); + }); + }); + }); }); From dc957ec10455f06ecd0b640dd0c52df7ef6a7682 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 11:04:33 +0100 Subject: [PATCH 111/119] CK-240: fix lint errors --- test/spec/ol/interaction/select.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index 65d47cea43..f648ad94ca 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -417,8 +417,8 @@ describe('ol.interaction.Select', function() { const style = new Style({}); const features = new Collection(); - firstInteraction = new Select({ style, features }); - secondInteraction = new Select({ style, features }); + firstInteraction = new Select({style, features}); + secondInteraction = new Select({style, features}); }); afterEach(function() { From 2d7e55e26abb4eb90cb89676adc1dd06e747aba7 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 13:44:43 +0100 Subject: [PATCH 112/119] Small code cleanup drop superfluous if. --- src/ol/interaction/Select.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/ol/interaction/Select.js b/src/ol/interaction/Select.js index a08c22bc54..9fde58ccbb 100644 --- a/src/ol/interaction/Select.js +++ b/src/ol/interaction/Select.js @@ -333,8 +333,7 @@ class Select extends Interaction { if (this.style_) { this.features_.forEach(this.applySelectedStyle_.bind(this)); } - } - if (!map) { + } else { this.features_.removeEventListener(CollectionEventType.ADD, this.boundAddFeature_); this.features_.removeEventListener(CollectionEventType.REMOVE, this.boundRemoveFeature_); } From e9e75cd8aff58ad96a0b7a93d16780ae0e54e0c2 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 15:31:33 +0100 Subject: [PATCH 113/119] temporarily disable test to observe impact --- test/spec/ol/interaction/select.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index f648ad94ca..be2d03cc93 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -408,7 +408,7 @@ describe('ol.interaction.Select', function() { }); - describe('clear event listeners on interaction removal', function() { + xdescribe('clear event listeners on interaction removal', function() { let firstInteraction, secondInteraction, feature; beforeEach(function() { From 3909938a706acba76263f514a6cb29cd7b3f63e4 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 15:37:27 +0100 Subject: [PATCH 114/119] Experiment with test impact further --- test/spec/ol/interaction/select.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index be2d03cc93..bc8aa66a97 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -408,7 +408,7 @@ describe('ol.interaction.Select', function() { }); - xdescribe('clear event listeners on interaction removal', function() { + describe('clear event listeners on interaction removal', function() { let firstInteraction, secondInteraction, feature; beforeEach(function() { @@ -441,7 +441,7 @@ describe('ol.interaction.Select', function() { }); // The "difficult" case. To prevent regression - describe('with a replaced interaction', function() { + xdescribe('with a replaced interaction', function() { it('changes the selected feature once', function() { map.addInteraction(firstInteraction); map.removeInteraction(firstInteraction); From cf1191505ead9cfd38aed30d2d93a150dac94f20 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 17:17:33 +0100 Subject: [PATCH 115/119] Experiment with test impact further (2) --- test/spec/ol/interaction/select.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index bc8aa66a97..06aa5b4fb5 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -427,7 +427,7 @@ describe('ol.interaction.Select', function() { }); // The base case - describe('with a single interaction added', function() { + xdescribe('with a single interaction added', function() { it('changes the selected feature once', function() { map.addInteraction(firstInteraction); @@ -441,7 +441,7 @@ describe('ol.interaction.Select', function() { }); // The "difficult" case. To prevent regression - xdescribe('with a replaced interaction', function() { + describe('with a replaced interaction', function() { it('changes the selected feature once', function() { map.addInteraction(firstInteraction); map.removeInteraction(firstInteraction); From ad77143417041c6ec93d8a8a287b0bfb96d7dcb0 Mon Sep 17 00:00:00 2001 From: Geert Premereur Date: Wed, 8 Jan 2020 22:31:31 +0100 Subject: [PATCH 116/119] Experiment with test impact further (3) --- test/spec/ol/interaction/select.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/spec/ol/interaction/select.test.js b/test/spec/ol/interaction/select.test.js index 06aa5b4fb5..f648ad94ca 100644 --- a/test/spec/ol/interaction/select.test.js +++ b/test/spec/ol/interaction/select.test.js @@ -427,7 +427,7 @@ describe('ol.interaction.Select', function() { }); // The base case - xdescribe('with a single interaction added', function() { + describe('with a single interaction added', function() { it('changes the selected feature once', function() { map.addInteraction(firstInteraction); From 5357b4fcedb188591d73c1dfe4d7402e1cb8c2d9 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Thu, 2 Apr 2020 22:03:53 +0200 Subject: [PATCH 117/119] Changelog for v6.3.0 --- changelog/upgrade-notes.md | 6 +- changelog/v6.3.0.md | 123 +++++++++++++++++++++++++++++++++++++ 2 files changed, 127 insertions(+), 2 deletions(-) create mode 100644 changelog/v6.3.0.md diff --git a/changelog/upgrade-notes.md b/changelog/upgrade-notes.md index 81c6eb6060..6ade599999 100644 --- a/changelog/upgrade-notes.md +++ b/changelog/upgrade-notes.md @@ -1,8 +1,10 @@ ## Upgrade notes -### v6.2.0 +### v6.3.0 -### v6.1.0 +#### Vector source loading when extent crosses +/-180 + +Previously, when an extent crossed the date line, vector source loaders were called with an extent with 540 degrees of longitude. Now, two loader calls with the visible extent on both sides of the projection extent are issued. This should not require any application code changes, but may affect custom loaders. ### v6.0.0 diff --git a/changelog/v6.3.0.md b/changelog/v6.3.0.md new file mode 100644 index 0000000000..1107121b15 --- /dev/null +++ b/changelog/v6.3.0.md @@ -0,0 +1,123 @@ +# 6.3.0 + +With more than 70 pull requests, this release not only brings significant improvements to the API documentation. It also fixes some old bugs and brings frequently requested improvments. And good news for TypeScript users: OpenLayers now ships with type definitions in `.d.ts` files. + +## New features and improvements + +* Several improvements to the Graticule layer, like consistent labeling, no more missing graticule lines, and it now works for views that cross the date line. +* Better support for KML icon colors, as well as fills and outlines in PolyStyle +* Better `ol/Overlay` performance and support for panning off-screen overlays into view +* Most of the rendering code can now be run in web workers, e.g. to render to an OffscreenCanvas +* OpenLayers now works fine in web components with shadow root +* WebGL point layers now support rotation based on feature attributes + +## List of all changes + + * [#10490](https://github.com/openlayers/openlayers/pull/10490) - Select style multiple select interactions removed ([@bepremeg](https://github.com/bepremeg)) + * [#10531](https://github.com/openlayers/openlayers/pull/10531) - Dynamically chose the number of subdivisions based on the size of the Image to reproject ([@pjsg](https://github.com/pjsg)) + * [#10618](https://github.com/openlayers/openlayers/pull/10618) - Add apidoc-debug task to debug the apidoc generation process ([@MoonE](https://github.com/MoonE)) + * [#10343](https://github.com/openlayers/openlayers/pull/10343) - Correct interactions with circle geometries when using user coordinates ([@mike-000](https://github.com/mike-000)) + * [#10864](https://github.com/openlayers/openlayers/pull/10864) - Update dependencies ([@ahocevar](https://github.com/ahocevar)) + * [#10859](https://github.com/openlayers/openlayers/pull/10859) - Add an example of clipping layer based on a vector source ([@SDaron](https://github.com/SDaron)) + * [#10850](https://github.com/openlayers/openlayers/pull/10850) - API docs for enums ([@ahocevar](https://github.com/ahocevar)) + * [#10857](https://github.com/openlayers/openlayers/pull/10857) - Make OSM XML example work at dateline and replace Bing with MapTiler ([@mike-000](https://github.com/mike-000)) + * [#10858](https://github.com/openlayers/openlayers/pull/10858) - Perform auto-pan when adding an Overlay to a Map ([@ejn](https://github.com/ejn)) + * [#10646](https://github.com/openlayers/openlayers/pull/10646) - Write fill and outline in KML PolyStyle ([@mike-000](https://github.com/mike-000)) + * [#10800](https://github.com/openlayers/openlayers/pull/10800) - Make Overlay.panIntoView an API method ([@ejn](https://github.com/ejn)) + * [#10807](https://github.com/openlayers/openlayers/pull/10807) - Handle Graticule wrapX without calculating excess meridians ([@mike-000](https://github.com/mike-000)) + * [#10795](https://github.com/openlayers/openlayers/pull/10795) - Show graticule labels in wrapped worlds ([@mike-000](https://github.com/mike-000)) + * [#10824](https://github.com/openlayers/openlayers/pull/10824) - Fix drawing svg icon with color option in ie11 ([@MoonE](https://github.com/MoonE)) + * [#10802](https://github.com/openlayers/openlayers/pull/10802) - Apidoc add default-exported enums ([@MoonE](https://github.com/MoonE)) + * [#10805](https://github.com/openlayers/openlayers/pull/10805) - make ImageSourceEventType available for consumers ([@regileeso](https://github.com/regileeso)) + * [#10822](https://github.com/openlayers/openlayers/pull/10822) - parsing color from IconStyle in KML files ([@lysek](https://github.com/lysek)) + * [#10848](https://github.com/openlayers/openlayers/pull/10848) - Speed up Overlay element positioning using CSS translate() ([@horsenit](https://github.com/horsenit)) + * [#9590](https://github.com/openlayers/openlayers/pull/9590) - Calculate tile grid extent from extent of bottom-level tile matrix ([@mloskot](https://github.com/mloskot)) + * [#10845](https://github.com/openlayers/openlayers/pull/10845) - Fix createHitDetectionImageData error for features with no size ([@gedaiu](https://github.com/gedaiu)) + * [#10842](https://github.com/openlayers/openlayers/pull/10842) - Fix custom symbol example short description ([@mike-000](https://github.com/mike-000)) + * [#10828](https://github.com/openlayers/openlayers/pull/10828) - Offscreen canvas example ([@ahocevar](https://github.com/ahocevar)) + * [#10816](https://github.com/openlayers/openlayers/pull/10816) - Add 'funding' field to `package.json` ([@marcjansen](https://github.com/marcjansen)) + * [#10813](https://github.com/openlayers/openlayers/pull/10813) - Add sponsors section to the readme ([@tschaub](https://github.com/tschaub)) + * [#10474](https://github.com/openlayers/openlayers/pull/10474) - Fix for undefined source in Image layer ([@mike-000](https://github.com/mike-000)) + * [#10785](https://github.com/openlayers/openlayers/pull/10785) - Detect Zoomify server-side retina tiles ([@ahocevar](https://github.com/ahocevar)) + * [#10787](https://github.com/openlayers/openlayers/pull/10787) - Improved projection extent in the "Reprojection with EPSG.io Search" example ([@mike-000](https://github.com/mike-000)) + * [#10792](https://github.com/openlayers/openlayers/pull/10792) - Add support for EventListener Object ([@flexjoly](https://github.com/flexjoly)) + * [#10777](https://github.com/openlayers/openlayers/pull/10777) - Keep the render loop running during simulation ([@ahocevar](https://github.com/ahocevar)) + * [#10791](https://github.com/openlayers/openlayers/pull/10791) - iOS 12 touchmove: Prevent touchmove event default when no preceding pointer event ([@sosmo](https://github.com/sosmo)) + * [#10786](https://github.com/openlayers/openlayers/pull/10786) - Resolve constraints when updating size ([@ahocevar](https://github.com/ahocevar)) + * [#10788](https://github.com/openlayers/openlayers/pull/10788) - Add safeguard to handleTouchMove ([@sosmo](https://github.com/sosmo)) + * [#10722](https://github.com/openlayers/openlayers/pull/10722) - fix: handle layer clear event in case clear(true) called ([@jellyedwards](https://github.com/jellyedwards)) + * [#10723](https://github.com/openlayers/openlayers/pull/10723) - Improve the extent transforms used by Graticule and handle extents crossing the dateline ([@mike-000](https://github.com/mike-000)) + * [#10744](https://github.com/openlayers/openlayers/pull/10744) - Ensure the Modify Features Test example opens at correct zoom ([@mike-000](https://github.com/mike-000)) + * [#10767](https://github.com/openlayers/openlayers/pull/10767) - Replace Bing layer with MapTiler in examples ([@mike-000](https://github.com/mike-000)) + * [#10751](https://github.com/openlayers/openlayers/pull/10751) - Sort events / observables in all cases ([@MoonE](https://github.com/MoonE)) + * [#10763](https://github.com/openlayers/openlayers/pull/10763) - TypeScript: Fix inconsistent optionality in various APIs ([@jumpinjackie](https://github.com/jumpinjackie)) + * [#10758](https://github.com/openlayers/openlayers/pull/10758) - Allow using feature attributes for symbol rotation in WebGL layers ([@jahow](https://github.com/jahow)) + * [#10748](https://github.com/openlayers/openlayers/pull/10748) - Fix "Cannot read property 'anchor' of undefined" in ol/View ([@mike-000](https://github.com/mike-000)) + * [#10746](https://github.com/openlayers/openlayers/pull/10746) - Fix building apidoc on windows ([@MoonE](https://github.com/MoonE)) + * [#10720](https://github.com/openlayers/openlayers/pull/10720) - Apidoc better search ([@MoonE](https://github.com/MoonE)) + * [#10743](https://github.com/openlayers/openlayers/pull/10743) - Ignore user provided tile cache size when too small ([@ahocevar](https://github.com/ahocevar)) + * [#10736](https://github.com/openlayers/openlayers/pull/10736) - Allow cluster source to unlisten from its source ([@M393](https://github.com/M393)) + * [#10739](https://github.com/openlayers/openlayers/pull/10739) - Fix typo in trackpad timeout ([@ahocevar](https://github.com/ahocevar)) + * [#10740](https://github.com/openlayers/openlayers/pull/10740) - Document tabindex behavior for MouseWheelZoom and DragPan ([@matthias-ccri](https://github.com/matthias-ccri)) + * [#10738](https://github.com/openlayers/openlayers/pull/10738) - Fix text background decluttering ([@ahocevar](https://github.com/ahocevar)) + * [#10715](https://github.com/openlayers/openlayers/pull/10715) - Fix disappearing graticule labels when rotation returns to 0 ([@mike-000](https://github.com/mike-000)) + * [#10713](https://github.com/openlayers/openlayers/pull/10713) - Draw graticule labels in a postrender function ([@mike-000](https://github.com/mike-000)) + * [#10711](https://github.com/openlayers/openlayers/pull/10711) - Make sure that optional args are typed accordingly ([@ahocevar](https://github.com/ahocevar)) + * [#10710](https://github.com/openlayers/openlayers/pull/10710) - Fix stylefunction return type ([@ahocevar](https://github.com/ahocevar)) + * [#10709](https://github.com/openlayers/openlayers/pull/10709) - Fix type and documentation of style function ([@ahocevar](https://github.com/ahocevar)) + * [#10708](https://github.com/openlayers/openlayers/pull/10708) - Handle Select interactions with falsey select style ([@ahocevar](https://github.com/ahocevar)) + * [#10707](https://github.com/openlayers/openlayers/pull/10707) - Get default projection for overview map from main map. ([@AugustusKling](https://github.com/AugustusKling)) + * [#10699](https://github.com/openlayers/openlayers/pull/10699) - Make Select interaction work when there are multiple instances ([@ahocevar](https://github.com/ahocevar)) + * [#10694](https://github.com/openlayers/openlayers/pull/10694) - Draw image with configured opacity ([@M393](https://github.com/M393)) + * [#10703](https://github.com/openlayers/openlayers/pull/10703) - CI and test fixes ([@ahocevar](https://github.com/ahocevar)) + * [#10698](https://github.com/openlayers/openlayers/pull/10698) - Shadow root ([@ahocevar](https://github.com/ahocevar)) + * [#10688](https://github.com/openlayers/openlayers/pull/10688) - Publish type definition files ([@ahocevar](https://github.com/ahocevar)) + * [#10691](https://github.com/openlayers/openlayers/pull/10691) - Do not exceed color range ([@ahocevar](https://github.com/ahocevar)) + * [#10683](https://github.com/openlayers/openlayers/pull/10683) - Dispatch enterfullscreen and leavefullscreen from the FullScreen control ([@fredj](https://github.com/fredj)) + * [#10676](https://github.com/openlayers/openlayers/pull/10676) - Document that overviewmap view must use same projection as main map ([@mike-000](https://github.com/mike-000)) + * [#10678](https://github.com/openlayers/openlayers/pull/10678) - Add maxResolution option to ol/tilegrid.createXYZ() and ol/source/XYZ ([@mike-000](https://github.com/mike-000)) + * [#10690](https://github.com/openlayers/openlayers/pull/10690) - Document minZoom and maxZoom options for all layers ([@mike-000](https://github.com/mike-000)) + * [#10672](https://github.com/openlayers/openlayers/pull/10672) - Nicer mousewheel and trackpad zooming ([@ahocevar](https://github.com/ahocevar)) + * [#10687](https://github.com/openlayers/openlayers/pull/10687) - Increase timeout in listenImage test ([@fredj](https://github.com/fredj)) + * [#10684](https://github.com/openlayers/openlayers/pull/10684) - perf: only do expensive reload when texture changes ([@jellyedwards](https://github.com/jellyedwards)) + * [#10675](https://github.com/openlayers/openlayers/pull/10675) - typo ([@jipexu](https://github.com/jipexu)) + * [#10669](https://github.com/openlayers/openlayers/pull/10669) - More browser compatible Export Map example ([@mike-000](https://github.com/mike-000)) + * [#10667](https://github.com/openlayers/openlayers/pull/10667) - Do not render label with the current linedash ([@ahocevar](https://github.com/ahocevar)) + * [#10666](https://github.com/openlayers/openlayers/pull/10666) - Load polyfill before example specific scripts in examples template ([@mike-000](https://github.com/mike-000)) + * [#6526](https://github.com/openlayers/openlayers/pull/6526) - Draw interaction: add abortDrawing method and drawabort event ([@tchandelle](https://github.com/tchandelle)) + * [#10657](https://github.com/openlayers/openlayers/pull/10657) - Changelog for v6.2.1 ([@openlayers](https://github.com/openlayers)) + + +
    + Dependency Updates + + * [#10855](https://github.com/openlayers/openlayers/pull/10855) - Bump rollup from 2.1.0 to 2.3.0 ([@openlayers](https://github.com/openlayers)) + * [#10854](https://github.com/openlayers/openlayers/pull/10854) - Bump ol-mapbox-style from 6.1.0 to 6.1.1 ([@openlayers](https://github.com/openlayers)) + * [#10853](https://github.com/openlayers/openlayers/pull/10853) - Bump buble from 0.19.8 to 0.20.0 ([@openlayers](https://github.com/openlayers)) + * [#10852](https://github.com/openlayers/openlayers/pull/10852) - Bump webpack from 4.42.0 to 4.42.1 ([@openlayers](https://github.com/openlayers)) + * [#10837](https://github.com/openlayers/openlayers/pull/10837) - Bump ol-mapbox-style from 6.0.1 to 6.1.0 ([@openlayers](https://github.com/openlayers)) + * [#10836](https://github.com/openlayers/openlayers/pull/10836) - Bump coveralls from 3.0.9 to 3.0.11 ([@openlayers](https://github.com/openlayers)) + * [#10835](https://github.com/openlayers/openlayers/pull/10835) - Bump @babel/preset-env from 7.8.7 to 7.9.0 ([@openlayers](https://github.com/openlayers)) + * [#10834](https://github.com/openlayers/openlayers/pull/10834) - Bump rollup from 1.32.1 to 2.1.0 ([@openlayers](https://github.com/openlayers)) + * [#10833](https://github.com/openlayers/openlayers/pull/10833) - Bump fs-extra from 8.1.0 to 9.0.0 ([@openlayers](https://github.com/openlayers)) + * [#10832](https://github.com/openlayers/openlayers/pull/10832) - Bump @babel/core from 7.8.7 to 7.9.0 ([@openlayers](https://github.com/openlayers)) + * [#10831](https://github.com/openlayers/openlayers/pull/10831) - Bump babel-loader from 8.0.6 to 8.1.0 ([@openlayers](https://github.com/openlayers)) + * [#10830](https://github.com/openlayers/openlayers/pull/10830) - Bump mocha from 7.1.0 to 7.1.1 ([@openlayers](https://github.com/openlayers)) + * [#10829](https://github.com/openlayers/openlayers/pull/10829) - Bump marked from 0.8.0 to 0.8.2 ([@openlayers](https://github.com/openlayers)) + * [#10811](https://github.com/openlayers/openlayers/pull/10811) - Bump sinon from 9.0.0 to 9.0.1 ([@openlayers](https://github.com/openlayers)) + * [#10810](https://github.com/openlayers/openlayers/pull/10810) - Bump rollup-plugin-terser from 5.2.0 to 5.3.0 ([@openlayers](https://github.com/openlayers)) + * [#10809](https://github.com/openlayers/openlayers/pull/10809) - Bump yargs from 15.3.0 to 15.3.1 ([@openlayers](https://github.com/openlayers)) + * [#10806](https://github.com/openlayers/openlayers/pull/10806) - [Security] Bump acorn from 6.1.1 to 6.4.1 ([@openlayers](https://github.com/openlayers)) + * [#10755](https://github.com/openlayers/openlayers/pull/10755) - Bump rollup from 1.31.1 to 1.32.0 ([@openlayers](https://github.com/openlayers)) + * [#10754](https://github.com/openlayers/openlayers/pull/10754) - Bump @babel/preset-env from 7.8.4 to 7.8.6 ([@openlayers](https://github.com/openlayers)) + * [#10753](https://github.com/openlayers/openlayers/pull/10753) - Bump mocha from 7.0.1 to 7.1.0 ([@openlayers](https://github.com/openlayers)) + * [#10752](https://github.com/openlayers/openlayers/pull/10752) - Bump @babel/core from 7.8.4 to 7.8.6 ([@openlayers](https://github.com/openlayers)) + * [#10725](https://github.com/openlayers/openlayers/pull/10725) - Bump elm-pep from 1.0.4 to 1.0.6 ([@openlayers](https://github.com/openlayers)) + * [#10726](https://github.com/openlayers/openlayers/pull/10726) - Bump sinon from 8.1.1 to 9.0.0 ([@openlayers](https://github.com/openlayers)) + * [#10680](https://github.com/openlayers/openlayers/pull/10680) - Bump terser-webpack-plugin from 2.3.4 to 2.3.5 ([@openlayers](https://github.com/openlayers)) + * [#10682](https://github.com/openlayers/openlayers/pull/10682) - Bump webpack from 4.41.5 to 4.41.6 ([@openlayers](https://github.com/openlayers)) + * [#10681](https://github.com/openlayers/openlayers/pull/10681) - Bump webpack-cli from 3.3.10 to 3.3.11 ([@openlayers](https://github.com/openlayers)) + * [#10679](https://github.com/openlayers/openlayers/pull/10679) - Bump rollup from 1.31.0 to 1.31.1 ([@openlayers](https://github.com/openlayers)) + + +
    From bdf969cc953f319ec7538db7fed50d8454866367 Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Thu, 2 Apr 2020 22:04:52 +0200 Subject: [PATCH 118/119] Update package version to 6.3.0 --- package-lock.json | 5 +++-- package.json | 2 +- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/package-lock.json b/package-lock.json index a4173b921a..2280550715 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "ol", - "version": "6.2.2", + "version": "6.3.0", "lockfileVersion": 1, "requires": true, "dependencies": { @@ -5971,7 +5971,8 @@ "dependencies": { "minimist": { "version": "1.2.0", - "resolved": "", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", "dev": true, "optional": true } diff --git a/package.json b/package.json index 7b1b6f52df..df5010c94a 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "ol", - "version": "6.2.2", + "version": "6.3.0", "description": "OpenLayers mapping library", "keywords": [ "map", From b71e8ebb73ca44c82d46d8d89f3b50aa8c5bf82e Mon Sep 17 00:00:00 2001 From: Andreas Hocevar Date: Thu, 2 Apr 2020 22:24:08 +0200 Subject: [PATCH 119/119] Develop on 6.3.1-dev --- package-lock.json | 2 +- package.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/package-lock.json b/package-lock.json index 2280550715..43de8147d9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "ol", - "version": "6.3.0", + "version": "6.3.1-dev", "lockfileVersion": 1, "requires": true, "dependencies": { diff --git a/package.json b/package.json index df5010c94a..f7fefb945c 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "ol", - "version": "6.3.0", + "version": "6.3.1-dev", "description": "OpenLayers mapping library", "keywords": [ "map",