diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 000000000..cd4efd8e5 --- /dev/null +++ b/.eslintignore @@ -0,0 +1 @@ +*.d.ts diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index ad5010766..7bd80bad1 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -13,5 +13,9 @@ jobs: - uses: actions/setup-node@v3 with: node-version: 18 + - name: CI + run: npm ci + - name: Lint + run: npm run lint - name: Pseudo release run: buildtools/release.sh diff --git a/package-lock.json b/package-lock.json index c1568463f..0676a8a42 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "ol-cesium", - "version": "2.16.0", + "version": "2.16.1", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "ol-cesium", - "version": "2.16.0", + "version": "2.16.1", "license": "BSD-2-Clause", "devDependencies": { "@babel/core": "7.23.6", diff --git a/package.json b/package.json index 57589fc08..2081cdd66 100644 --- a/package.json +++ b/package.json @@ -9,6 +9,7 @@ "build-umd": "cross-env NODE_ENV=production TARGET=umd webpack --progress --bail", "start": "cross-env DEV_SERVER=1 NODE_ENV=development TARGET=examples webpack serve --port 3000 --progress --bail --static-directory .", "typecheck": "tsc --pretty", + "lint": "eslint src", "doc": "typedoc --name ol-cesium --excludeExternals --out dist/apidoc --entryPoints src/index.library.js --tsconfig ./tsconfig.json" }, "main": "./dist/olcesium.js", diff --git a/src/olcs/AbstractSynchronizer.ts b/src/olcs/AbstractSynchronizer.ts index fb39abcd8..42e14ff8a 100644 --- a/src/olcs/AbstractSynchronizer.ts +++ b/src/olcs/AbstractSynchronizer.ts @@ -28,7 +28,7 @@ abstract class AbstractSynchronizer> = {}; + protected olLayerListenKeys: Record> = {}; /** * Map of listen keys for OpenLayers layer groups ids (from getUid). */ diff --git a/src/olcs/OLCesium.ts b/src/olcs/OLCesium.ts index 3292b7255..d56650e95 100644 --- a/src/olcs/OLCesium.ts +++ b/src/olcs/OLCesium.ts @@ -46,7 +46,7 @@ const BoundingSphereState: Record = { * The BoundingSphere does not exist. */ FAILED: 2, -} +}; type SceneOptions = { canvas: HTMLCanvasElement; @@ -130,7 +130,7 @@ class OLCesium { constructor(options: OLCesiumOptions) { this.map_ = options.map; - this.time_ = options.time || function () { + this.time_ = options.time || function() { return Cesium.JulianDate.now(); }; @@ -176,10 +176,10 @@ class OLCesium { this.canvas_.style['imageRendering'] = imageRenderingValue(); } - this.canvas_.oncontextmenu = function () { + this.canvas_.oncontextmenu = function() { return false; }; - this.canvas_.onselectstart = function () { + this.canvas_.onselectstart = function() { return false; }; @@ -382,7 +382,7 @@ class OLCesium { this.canvas_.width = width; this.canvas_.height = height; - (this.scene_.camera.frustum).aspectRatio = width / height; + ( this.scene_.camera.frustum).aspectRatio = width / height; } getCamera(): olcsCamera { @@ -440,14 +440,14 @@ class OLCesium { this.map_.addInteraction = interaction => this.pausedInteractions_.push(interaction); this.map_.removeInteraction = (interaction) => { - let interactionRemoved = false + let interactionRemoved = false; this.pausedInteractions_ = this.pausedInteractions_.filter((i) => { const removed = i !== interaction; - if(!interactionRemoved) interactionRemoved = removed - return removed - }) + if (!interactionRemoved) {interactionRemoved = removed;} + return removed; + }); return interactionRemoved ? interaction : undefined; - } + }; const rootGroup = this.map_.getLayerGroup(); if (rootGroup.getVisible()) { diff --git a/src/olcs/RasterSynchronizer.ts b/src/olcs/RasterSynchronizer.ts index 55915969d..7c284d4f3 100644 --- a/src/olcs/RasterSynchronizer.ts +++ b/src/olcs/RasterSynchronizer.ts @@ -95,10 +95,10 @@ class RasterSynchronizer extends olcsAbstractSynchronizer { const ip = csObj.imageryProvider; if (ip) { - // @ts-ignore TS2341 - ip.tileCache?.clear(); - // @ts-ignore TS2341 - ip.styleFunction_ = currentStyleFunction; + // @ts-ignore TS2341 + ip.tileCache?.clear(); + // @ts-ignore TS2341 + ip.styleFunction_ = currentStyleFunction; } } this.scene.requestRender(); diff --git a/src/olcs/VectorSynchronizer.ts b/src/olcs/VectorSynchronizer.ts index a403a6551..74094302d 100644 --- a/src/olcs/VectorSynchronizer.ts +++ b/src/olcs/VectorSynchronizer.ts @@ -21,7 +21,7 @@ import {Primitive, PrimitiveCollection, Scene} from 'cesium'; class VectorSynchronizer extends olcsAbstractSynchronizer { protected converter: olcsFeatureConverter; - private csAllPrimitives_: PrimitiveCollection + private csAllPrimitives_: PrimitiveCollection; /** * Unidirectionally synchronize OpenLayers vector layers to Cesium. */ @@ -36,7 +36,7 @@ class VectorSynchronizer extends olcsAbstractSynchronizercounterpart.getRootPrimitive() + const collection = counterpart.getRootPrimitive(); collection.counterpart = counterpart; this.csAllPrimitives_.add(counterpart.getRootPrimitive()); } diff --git a/src/olcs/core.ts b/src/olcs/core.ts index 898b6a0c1..28435d954 100644 --- a/src/olcs/core.ts +++ b/src/olcs/core.ts @@ -403,7 +403,7 @@ export function sourceToImageryProvider( source.getImageExtent()[2], source.getImageExtent()[3], new Cesium.Rectangle() - ) + ); provider = new Cesium.SingleTileImageryProvider({ url: source.getUrl(), rectangle @@ -456,7 +456,7 @@ export function sourceToImageryProvider( * Creates Cesium.ImageryLayer best corresponding to the given ol.layer.Layer. * Only supports raster layers and export function images */ -export function tileLayerToImageryLayer(olMap: Map, olLayer: BaseLayer, viewProj: Projection): ImageryLayer | null { +export function tileLayerToImageryLayer(olMap: Map, olLayer: BaseLayer, viewProj: Projection): ImageryLayer | null { if (!(olLayer instanceof olLayerTile) && !(olLayer instanceof olLayerImage) && !(olLayer instanceof VectorTileLayer)) { @@ -784,7 +784,7 @@ export function calcResolutionForDistance(distance: number, latitude: number, sc */ export function limitCameraToBoundingSphere(camera: Camera, boundingSphere: BoundingSphere, ratio: (height: number) => number): () => void { let blockLimiter = false; - return function () { + return function() { if (!blockLimiter) { const position = camera.position; const carto = Cesium.Cartographic.fromCartesian(position); diff --git a/src/olcs/core/VectorLayerCounterpart.ts b/src/olcs/core/VectorLayerCounterpart.ts index d7c74c8a5..9c6120c40 100644 --- a/src/olcs/core/VectorLayerCounterpart.ts +++ b/src/olcs/core/VectorLayerCounterpart.ts @@ -17,11 +17,9 @@ export type OlFeatureToCesiumContext = { primitives: PrimitiveCollection }; -export type PrimitiveCollectionCounterpart = PrimitiveCollection & {counterpart: VectorLayerCounterpart}; - class VectorLayerCounterpart { - olListenKeys: EventsKey[] = [] + olListenKeys: EventsKey[] = []; context: OlFeatureToCesiumContext; private rootCollection_: PrimitiveCollection; /** @@ -57,3 +55,4 @@ class VectorLayerCounterpart { export default VectorLayerCounterpart; +export type PrimitiveCollectionCounterpart = PrimitiveCollection & {counterpart: VectorLayerCounterpart}; diff --git a/src/olcs/print/drawCesiumMask.ts b/src/olcs/print/drawCesiumMask.ts index fd5cfb24f..8d0df9d29 100644 --- a/src/olcs/print/drawCesiumMask.ts +++ b/src/olcs/print/drawCesiumMask.ts @@ -12,29 +12,6 @@ interface ProgramInfo { } } -/** - * - */ -export function autoDrawMask(scene: Scene, getScalings: () => number[]) { - const canvas = scene.canvas; - const ctx = canvas.getContext("webgl2") || canvas.getContext("webgl"); - - if (getScalings) { - if (!postUnlistener) { - const drawer = new MaskDrawer(ctx); - postUnlistener = scene.postRender.addEventListener(() => { - drawer.drawMask(getScalings()); - }); - } - } - else if (postUnlistener) { - postUnlistener(); - // FIXME: destroy program - postUnlistener = null; - } - scene.requestRender(); -} - // CC0 from https://github.com/mdn/dom-examples/tree/main/webgl-examples/tutorial/sample2 @@ -49,12 +26,12 @@ export class MaskDrawer { this.programInfo = { program: shaderProgram, attribLocations: { - vertexPosition: gl.getAttribLocation(shaderProgram, "aVertexPosition") + vertexPosition: gl.getAttribLocation(shaderProgram, 'aVertexPosition') }, uniformLocations: { uScaling: gl.getUniformLocation( - shaderProgram, - "uScaling" + shaderProgram, + 'uScaling' ) } }; @@ -93,8 +70,8 @@ export class MaskDrawer { const vsSource = this.getVertexShaderSource(); const fsSource = this.getFragmentShaderSource(); const vertexShader = MaskDrawer.loadShader(gl, gl.VERTEX_SHADER, vsSource), - fragmentShader = MaskDrawer.loadShader(gl, gl.FRAGMENT_SHADER, fsSource), - shaderProgram = gl.createProgram(); + fragmentShader = MaskDrawer.loadShader(gl, gl.FRAGMENT_SHADER, fsSource), + shaderProgram = gl.createProgram(); gl.attachShader(shaderProgram, vertexShader); gl.attachShader(shaderProgram, fragmentShader); @@ -104,9 +81,9 @@ export class MaskDrawer { if (!gl.getProgramParameter(shaderProgram, gl.LINK_STATUS)) { throw new Error( - `Unable to initialize the shader program: ${gl.getProgramInfoLog( - shaderProgram - )}` + `Unable to initialize the shader program: ${gl.getProgramInfoLog( + shaderProgram + )}` ); } @@ -126,12 +103,12 @@ export class MaskDrawer { gl.bindBuffer(gl.ARRAY_BUFFER, this.positionBuffer); gl.vertexAttribPointer( - programInfo.attribLocations.vertexPosition, - 2, - gl.FLOAT, - false, - 0, - 0 + programInfo.attribLocations.vertexPosition, + 2, + gl.FLOAT, + false, + 0, + 0 ); gl.enableVertexAttribArray(programInfo.attribLocations.vertexPosition); gl.useProgram(programInfo.program); @@ -140,18 +117,18 @@ export class MaskDrawer { // Draw a first time to fill the stencil area while keeping the destination color gl.enable(gl.STENCIL_TEST); gl.stencilFunc( - gl.ALWAYS, - 1, - 0xFF + gl.ALWAYS, + 1, + 0xFF ); gl.stencilOp( - gl.KEEP, - gl.KEEP, - gl.REPLACE + gl.KEEP, + gl.KEEP, + gl.REPLACE ); gl.uniform2fv( - programInfo.uniformLocations.uScaling, - scaling + programInfo.uniformLocations.uScaling, + scaling ); gl.blendFunc(gl.ZERO, gl.ONE); gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4); @@ -159,18 +136,18 @@ export class MaskDrawer { // Now draw again the whole viewport and darken the pixels that are not on the stencil gl.stencilFunc( - gl.EQUAL, - 0, - 0xFF + gl.EQUAL, + 0, + 0xFF ); gl.stencilOp( - gl.KEEP, - gl.KEEP, - gl.KEEP + gl.KEEP, + gl.KEEP, + gl.KEEP ); gl.uniform2fv( - programInfo.uniformLocations.uScaling, - [1, 1] + programInfo.uniformLocations.uScaling, + [1, 1] ); gl.blendFunc(gl.ZERO, gl.SRC_ALPHA); gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4); @@ -188,7 +165,7 @@ export class MaskDrawer { if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS)) { throw new Error( - `An error occurred compiling the shaders: ${gl.getShaderInfoLog(shader)}` + `An error occurred compiling the shaders: ${gl.getShaderInfoLog(shader)}` ); // gl.deleteShader(shader); } @@ -196,3 +173,26 @@ export class MaskDrawer { return shader; } } + +/** + * + */ +export function autoDrawMask(scene: Scene, getScalings: () => number[]) { + const canvas = scene.canvas; + const ctx = canvas.getContext('webgl2') || canvas.getContext('webgl'); + + if (getScalings) { + if (!postUnlistener) { + const drawer = new MaskDrawer(ctx); + postUnlistener = scene.postRender.addEventListener(() => { + drawer.drawMask(getScalings()); + }); + } + } + else if (postUnlistener) { + postUnlistener(); + // FIXME: destroy program + postUnlistener = null; + } + scene.requestRender(); +} diff --git a/src/olcs/print/takeCesiumScreenshot.ts b/src/olcs/print/takeCesiumScreenshot.ts index 6be3360ae..5fed06998 100644 --- a/src/olcs/print/takeCesiumScreenshot.ts +++ b/src/olcs/print/takeCesiumScreenshot.ts @@ -12,32 +12,32 @@ interface ScreenshotOptions { export function takeScreenshot(scene: Scene, options: ScreenshotOptions): Promise { return new Promise((resolve, reject) => { // preserveDrawingBuffers is false so we render on demand and immediately read the buffer - const remover = scene.postRender.addEventListener(() => { - remover(); - try { - let url; + const remover = scene.postRender.addEventListener(() => { + remover(); + try { + let url; - if (options) { - const smallerCanvas = document.createElement("canvas"); + if (options) { + const smallerCanvas = document.createElement('canvas'); - smallerCanvas.width = options.width; - smallerCanvas.height = options.height; - smallerCanvas.getContext("2d").drawImage( - scene.canvas, - options.offsetX, options.offsetY, options.width, options.height, - 0, 0, options.width, options.height); - url = smallerCanvas.toDataURL(); - } - else { - url = scene.canvas.toDataURL(); - } - resolve(url); - } - catch (e) { - reject(e); - } - }); + smallerCanvas.width = options.width; + smallerCanvas.height = options.height; + smallerCanvas.getContext('2d').drawImage( + scene.canvas, + options.offsetX, options.offsetY, options.width, options.height, + 0, 0, options.width, options.height); + url = smallerCanvas.toDataURL(); + } + else { + url = scene.canvas.toDataURL(); + } + resolve(url); + } + catch (e) { + reject(e); + } + }); - scene.requestRender(); + scene.requestRender(); }); }