diff --git a/.eslintrc.json b/.eslintrc.json index 7944ce060..09e42794d 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -6,6 +6,7 @@ "parserOptions": { "ecmaVersion": "latest" }, + "rules": { "comma-dangle": [ "error", diff --git a/css/svg/origo-icons.svg b/css/svg/origo-icons.svg index 39bb9ac64..f082231c8 100644 --- a/css/svg/origo-icons.svg +++ b/css/svg/origo-icons.svg @@ -4,4 +4,5 @@ + diff --git a/package-lock.json b/package-lock.json index d4e3f8376..26e371c95 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2639,9 +2639,9 @@ "dev": true }, "follow-redirects": { - "version": "1.14.8", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.8.tgz", - "integrity": "sha512-1x0S9UVJHsQprFcEC/qnNzBLcIxsjAV905f/UkQxbclCsoTWlacCNOpQa/anodLl2uaEKFhfWOvM2Qg77+15zA==", + "version": "1.15.4", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.4.tgz", + "integrity": "sha512-Cr4D/5wlrb0z9dgERpUL3LrmPKVDsETIJhaCMeDfuFYcqa5bldGV6wBsAN6X/vxlXQtFBMrXdXxdL8CbDTGniw==", "dev": true }, "forwarded": { diff --git a/scss/_infowindow.scss b/scss/_infowindow.scss index 8720420b7..3325a9ec3 100644 --- a/scss/_infowindow.scss +++ b/scss/_infowindow.scss @@ -174,6 +174,7 @@ .o-identify-content { display: inline-block; width: 100%; + overflow-wrap: anywhere; } .folded { diff --git a/src/controls/legend/overlay.js b/src/controls/legend/overlay.js index 5e3ca05ba..ced8c33f6 100644 --- a/src/controls/legend/overlay.js +++ b/src/controls/legend/overlay.js @@ -6,7 +6,7 @@ const OverlayLayer = function OverlayLayer(options) { const { headerIconCls = '', cls: clsSettings = '', - icon = '#o_list_24px', + icon = '#o_legend_24px', iconCls = 'grey-lightest', layer, position = 'top', diff --git a/src/controls/print/print-component.js b/src/controls/print/print-component.js index c4d256f1c..54a3d6779 100644 --- a/src/controls/print/print-component.js +++ b/src/controls/print/print-component.js @@ -271,7 +271,8 @@ const PrintComponent = function PrintComponent(options = {}) { titleComponent, descriptionComponent, createdComponent, - closeButton + closeButton, + constrainResolution: view.getConstrainResolution() }); const setScale = function setScale(scale) { diff --git a/src/controls/print/print-resize.js b/src/controls/print/print-resize.js index 46eea5490..fed76174e 100644 --- a/src/controls/print/print-resize.js +++ b/src/controls/print/print-resize.js @@ -19,7 +19,8 @@ export default function PrintResize(options = {}) { titleComponent, descriptionComponent, createdComponent, - closeButton + closeButton, + constrainResolution } = options; let { @@ -404,6 +405,8 @@ export default function PrintResize(options = {}) { // Alters layer in map, if vector then set scale for feature, if image set DPI parameter for source const setLayerScale = function setLayerScale(layer) { const source = layer.getSource(); + const view = map.getView(); + view.setConstrainResolution(false); if (isVector(layer)) { const styleName = layer.get('styleName'); @@ -467,6 +470,8 @@ export default function PrintResize(options = {}) { // "Resets" layer by resetting the style and removing DPI parameter const resetLayerScale = function resetLayerScale(layer) { const source = layer.getSource(); + const view = map.getView(); + view.setConstrainResolution(constrainResolution); if (isVector(layer)) { const features = source.getFeatures(); const styleName = layer.get('styleName'); diff --git a/src/style/drawstyles.js b/src/style/drawstyles.js index 1c7c736b6..a27f26f27 100644 --- a/src/style/drawstyles.js +++ b/src/style/drawstyles.js @@ -10,7 +10,7 @@ import { import { getArea, getLength } from 'ol/sphere'; import { LineString, MultiPoint, Point } from 'ol/geom'; -function createRegularShape(type, pointSize, pointFill, pointStroke) { +function createRegularShape(type, pointSize, pointFill, pointStroke, pointRotation) { let style; const size = pointSize || 10; const stroke = pointStroke || new Stroke({ @@ -19,6 +19,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { const fill = pointFill || new Fill({ color: 'rgba(0, 153, 255, 0.8)' }); + const rotation = pointRotation || 0; switch (type) { case 'square': style = new Style({ @@ -27,6 +28,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { stroke, points: 4, radius: size, + rotation: (rotation / 360) * Math.PI, angle: Math.PI / 4 }) }); @@ -39,7 +41,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { stroke, points: 3, radius: size, - rotation: 0, + rotation: (rotation / 360) * Math.PI, angle: 0 }) }); @@ -53,6 +55,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { points: 5, radius: size, radius2: size / 2.5, + rotation: (rotation / 360) * Math.PI, angle: 0 }) }); @@ -66,6 +69,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { points: 4, radius: size, radius2: 0, + rotation: (rotation / 360) * Math.PI, angle: 0 }) }); @@ -79,6 +83,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { points: 4, radius: size, radius2: 0, + rotation: (rotation / 360) * Math.PI, angle: Math.PI / 4 }) }); @@ -112,6 +117,7 @@ function createRegularShape(type, pointSize, pointFill, pointStroke) { image: new Icon({ src: `data:image/svg+xml;utf8,${svg}`, scale: size / 10 || 1, + rotation: (rotation / 360) * Math.PI, anchor: [0.5, 0.85] }) }); diff --git a/src/style/styletemplate.js b/src/style/styletemplate.js index 81846e257..da92b8161 100644 --- a/src/style/styletemplate.js +++ b/src/style/styletemplate.js @@ -1,6 +1,7 @@ export default function styleTemplate(palette, swStyle) { const colorArray = palette; let fillHtml = '
Fyllning
`; + backgroundFillHtml += `
+ +
+ 0% + Opacitet + 100% +
+
`; + let strokeHtml = '
Kantlinje
`; + let backgroundStrokeHtml = '
Bakgrundsram
+ +
+ 0% + Opacitet + 100% +
+
+
+ +
+ 1px + Linjebredd + 10px +
+
+
+ +
`; + const pointHtml = `
Punkt
@@ -101,5 +149,23 @@ export default function styleTemplate(palette, swStyle) {
`; - return textHtml + pointHtml + fillHtml + strokeHtml + measureHtml; + const rotateHtml = `
Rotation
+ +
+ + Graders rotation + 360° +
+
`; + + const paddingHtml = `
Marginaler
+ +
+ 0px + Marginal till text + 30px +
+
`; + + return textHtml + pointHtml + fillHtml + strokeHtml + measureHtml + rotateHtml + backgroundFillHtml + backgroundStrokeHtml + paddingHtml; } diff --git a/src/style/stylewindow.js b/src/style/stylewindow.js index 8878a6371..a13882175 100644 --- a/src/style/stylewindow.js +++ b/src/style/stylewindow.js @@ -37,7 +37,15 @@ const Stylewindow = function Stylewindow(optOptions = {}) { textFont: '"Helvetica Neue", Helvetica, Arial, sans-serif', showMeasureSegments: false, showMeasure: false, - selected: false + selected: false, + objRotation: 0, + backgroundFillColor: 'rgb(255,255,255)', + backgroundFillOpacity: 0, + backgroundStrokeColor: 'rgb(0,0,0)', + backgroundStrokeOpacity: 0, + backgroundStrokeWidth: 2, + backgroundStrokeType: 'line', + paddingText: 3 }; function escapeQuotes(s) { @@ -77,6 +85,10 @@ const Stylewindow = function Stylewindow(optOptions = {}) { return rgbToRgba(swDefaults.fillColor, swDefaults.fillOpacity); } + function paddingToArray(padding) { + return [padding, padding, padding, padding]; + } + function setFillColor(color) { swStyle.fillColor = rgbToRgba(color, swStyle.fillOpacity); } @@ -85,6 +97,30 @@ const Stylewindow = function Stylewindow(optOptions = {}) { swStyle.strokeColor = rgbToRgba(color, swStyle.strokeOpacity); } + function setBackgroundFillColor(color, opacity) { + if (typeof opacity === 'undefined') { + if (swStyle.backgroundFillOpacity === '0') { + swStyle.backgroundFillColor = rgbToRgba(color, 0.7); + swStyle.backgroundFillOpacity = 0.7; + document.getElementById('o-draw-style-backgroundFillOpacitySlider').value = 0.7; + } else { + swStyle.backgroundFillColor = rgbToRgba(color, swStyle.backgroundFillOpacity); + } + } else { + swStyle.backgroundFillColor = rgbToRgba(color, opacity); + } + } + + function setBackgroundStrokeColor(color) { + if (swStyle.backgroundStrokeOpacity === 0) { + swStyle.backgroundStrokeColor = rgbToRgba(color, 0.7); + swStyle.backgroundStrokeOpacity = 0.7; + document.getElementById('o-draw-style-backgroundStrokeOpacitySlider').value = 0.7; + } else { + swStyle.backgroundStrokeColor = rgbToRgba(color, swStyle.backgroundStrokeOpacity); + } + } + function getStyleObject(feature, selected = false) { let geometryType = feature.getGeometry().getType(); let styleObject = {}; @@ -124,6 +160,7 @@ const Stylewindow = function Stylewindow(optOptions = {}) { strokeType: swStyle.strokeType, pointSize: swStyle.pointSize, pointType: swStyle.pointType, + objRotation: swStyle.objRotation, selected }; break; @@ -133,6 +170,13 @@ const Stylewindow = function Stylewindow(optOptions = {}) { textSize: swStyle.textSize, textString: swStyle.textString, textFont: swStyle.textFont, + objRotation: swStyle.objRotation, + backgroundFill: rgbToRgba(swStyle.backgroundFillColor, swStyle.backgroundFillOpacity), + backgroundStrokeColor: swStyle.backgroundStrokeColor, + backgroundStrokeOpacity: swStyle.backgroundStrokeOpacity, + backgroundStrokeWidth: swStyle.backgroundStrokeWidth, + backgroundStrokeType: swStyle.backgroundStrokeType, + paddingText: swStyle.paddingText, selected }; break; @@ -150,6 +194,10 @@ const Stylewindow = function Stylewindow(optOptions = {}) { document.getElementById('o-draw-style-point').classList.remove('hidden'); document.getElementById('o-draw-style-text').classList.remove('hidden'); document.getElementById('o-draw-style-measure').classList.remove('hidden'); + document.getElementById('o-draw-style-rotation').classList.remove('hidden'); + document.getElementById('o-draw-style-backgroundFill').classList.remove('hidden'); + document.getElementById('o-draw-style-backgroundStroke').classList.remove('hidden'); + document.getElementById('o-draw-style-padding').classList.remove('hidden'); } function updateStylewindow(feature) { @@ -167,16 +215,27 @@ const Stylewindow = function Stylewindow(optOptions = {}) { document.getElementById('o-draw-style-fill').classList.add('hidden'); document.getElementById('o-draw-style-point').classList.add('hidden'); document.getElementById('o-draw-style-text').classList.add('hidden'); + document.getElementById('o-draw-style-rotation').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundFill').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundStroke').classList.add('hidden'); + document.getElementById('o-draw-style-padding').classList.add('hidden'); break; case 'Polygon': case 'MultiPolygon': document.getElementById('o-draw-style-point').classList.add('hidden'); document.getElementById('o-draw-style-text').classList.add('hidden'); + document.getElementById('o-draw-style-rotation').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundFill').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundStroke').classList.add('hidden'); + document.getElementById('o-draw-style-padding').classList.add('hidden'); break; case 'Point': case 'MultiPoint': document.getElementById('o-draw-style-text').classList.add('hidden'); document.getElementById('o-draw-style-measure').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundFill').classList.add('hidden'); + document.getElementById('o-draw-style-backgroundStroke').classList.add('hidden'); + document.getElementById('o-draw-style-padding').classList.add('hidden'); break; case 'TextPoint': document.getElementById('o-draw-style-stroke').classList.add('hidden'); @@ -190,6 +249,8 @@ const Stylewindow = function Stylewindow(optOptions = {}) { document.getElementById('o-draw-style-pointType').value = swStyle.pointType; document.getElementById('o-draw-style-textSizeSlider').value = swStyle.textSize; document.getElementById('o-draw-style-textString').value = swStyle.textString; + document.getElementById('o-draw-style-rotationSlider').value = swStyle.objRotation; + document.getElementById('o-draw-style-padding').value = swStyle.paddingText; swStyle.strokeOpacity = rgbaToOpacity(swStyle.strokeColor); swStyle.strokeColor = rgbaToRgb(swStyle.strokeColor); const strokeEl = document.getElementById('o-draw-style-strokeColor'); @@ -206,6 +267,21 @@ const Stylewindow = function Stylewindow(optOptions = {}) { document.getElementById('o-draw-style-strokeOpacitySlider').value = swStyle.strokeOpacity; document.getElementById('o-draw-style-strokeType').value = swStyle.strokeType; + swStyle.backgroundStrokeColor = rgbaToRgb(swStyle.backgroundStrokeColor); + const bgStrokeEl = document.getElementById('o-draw-style-strokeColor'); + const bgStrokeInputEl = bgStrokeEl.querySelector(`input[value = "${swStyle.backgroundStrokeColor}"]`); + if (bgStrokeInputEl) { + bgStrokeInputEl.checked = true; + } else { + const checkedEl = document.querySelector('input[name = "backgroundStrokeColorRadio"]:checked'); + if (checkedEl) { + checkedEl.checked = false; + } + } + document.getElementById('o-draw-style-backgroundStrokeWidthSlider').value = swStyle.backgroundStrokeWidth; + document.getElementById('o-draw-style-backgroundStrokeOpacitySlider').value = swStyle.backgroundStrokeOpacity; + document.getElementById('o-draw-style-backgroundStrokeType').value = swStyle.backgroundStrokeType; + const fillEl = document.getElementById('o-draw-style-fillColor'); swStyle.fillOpacity = rgbaToOpacity(swStyle.fillColor); swStyle.fillColor = rgbaToRgb(swStyle.fillColor); @@ -221,6 +297,22 @@ const Stylewindow = function Stylewindow(optOptions = {}) { document.getElementById('o-draw-style-fillOpacitySlider').value = swStyle.fillOpacity; document.getElementById('o-draw-style-showMeasure').checked = swStyle.showMeasure; document.getElementById('o-draw-style-showMeasureSegments').checked = swStyle.showMeasureSegments; + + const bgFillEl = document.getElementById('o-draw-style-backgroundFillColor'); + if (typeof swStyle.backgroundFill !== 'undefined') { + swStyle.backgroundFillOpacity = rgbaToOpacity(swStyle.backgroundFill); + swStyle.backgroundFillColor = rgbaToRgb(swStyle.backgroundFill); + } + const bgFillInputEl = bgFillEl.querySelector(`input[value = "${swStyle.backgroundFillColor}"]`); + if (bgFillInputEl) { + bgFillInputEl.checked = true; + } else { + const checkedEl = document.querySelector('input[name = "backgroundFillColorRadio"]:checked'); + if (checkedEl) { + checkedEl.checked = false; + } + } + document.getElementById('o-draw-style-backgroundFillOpacitySlider').value = swStyle.backgroundFillOpacity; } function getStyleFunction(feature, inputStyle = {}, projection = mapProjection) { @@ -235,6 +327,10 @@ const Stylewindow = function Stylewindow(optOptions = {}) { newStyleObj.strokeWidth *= styleScale; newStyleObj.textSize *= styleScale; newStyleObj.pointSize *= styleScale; + newStyleObj.backgroundStrokeOpacity = featureStyle.backgroundStrokeOpacity; + newStyleObj.backgroundStrokeColor = stringToRgba(newStyleObj.backgroundStrokeColor, newStyleObj.backgroundStrokeOpacity); + newStyleObj.backgroundStrokeWidth *= styleScale; + newStyleObj.paddingText = paddingToArray(featureStyle.paddingText); const geom = feature.getGeometry(); let geometryType = feature.getGeometry().getType(); if (feature.get(annotationField)) { @@ -251,6 +347,16 @@ const Stylewindow = function Stylewindow(optOptions = {}) { } else { lineDash = false; } + let bgLineDash; + if (newStyleObj.backgroundStrokeType === 'dash') { + bgLineDash = [3 * newStyleObj.backgroundStrokeWidth, 3 * newStyleObj.backgroundStrokeWidth]; + } else if (newStyleObj.backgroundStrokeType === 'dash-point') { + bgLineDash = [3 * newStyleObj.backgroundStrokeWidth, 3 * newStyleObj.backgroundStrokeWidth, 0.1, 3 * newStyleObj.backgroundStrokeWidth]; + } else if (newStyleObj.backgroundStrokeType === 'point') { + bgLineDash = [0.1, 3 * newStyleObj.backgroundStrokeWidth]; + } else { + bgLineDash = false; + } const stroke = new Stroke({ color: newStyleObj.strokeColor, @@ -260,6 +366,14 @@ const Stylewindow = function Stylewindow(optOptions = {}) { const fill = new Fill({ color: newStyleObj.fillColor }); + const bgStroke = new Stroke({ + color: rgbToArray(newStyleObj.backgroundStrokeColor, newStyleObj.backgroundStrokeOpacity), + width: newStyleObj.backgroundStrokeWidth, + lineDash: bgLineDash + }); + const bgFill = new Fill({ + color: newStyleObj.backgroundFill + }); const font = `${newStyleObj.textSize}px ${newStyleObj.textFont}`; switch (geometryType) { case 'LineString': @@ -353,14 +467,18 @@ const Stylewindow = function Stylewindow(optOptions = {}) { break; case 'Point': case 'MultiPoint': - style[0] = drawStyles.createRegularShape(newStyleObj.pointType, newStyleObj.pointSize, fill, stroke); + style[0] = drawStyles.createRegularShape(newStyleObj.pointType, newStyleObj.pointSize, fill, stroke, newStyleObj.objRotation); break; case 'TextPoint': style[0] = new Style({ text: new Text({ text: newStyleObj.textString || 'Text', font, - fill + fill, + rotation: (newStyleObj.objRotation / 360) * Math.PI || 0, + backgroundFill: bgFill, + backgroundStroke: bgStroke, + padding: newStyleObj.paddingText }) }); feature.set(annotationField, newStyleObj.textString || 'Text'); @@ -402,6 +520,8 @@ const Stylewindow = function Stylewindow(optOptions = {}) { let matches; const fillColorEl = document.getElementById('o-draw-style-fillColor'); const strokeColorEl = document.getElementById('o-draw-style-strokeColor'); + const bgFillColorEl = document.getElementById('o-draw-style-backgroundFillColor'); + const bgStrokeColorEl = document.getElementById('o-draw-style-backgroundStrokeColor'); matches = fillColorEl.querySelectorAll('span'); for (let i = 0; i < matches.length; i += 1) { @@ -419,6 +539,22 @@ const Stylewindow = function Stylewindow(optOptions = {}) { }); } + matches = bgFillColorEl.querySelectorAll('span'); + for (let i = 0; i < matches.length; i += 1) { + matches[i].addEventListener('click', function e() { + setBackgroundFillColor(this.style.backgroundColor); + styleSelectedFeatures(); + }); + } + + matches = bgStrokeColorEl.querySelectorAll('span'); + for (let i = 0; i < matches.length; i += 1) { + matches[i].addEventListener('click', function e() { + setBackgroundStrokeColor(this.style.backgroundColor); + styleSelectedFeatures(); + }); + } + document.getElementById('o-draw-style-fillOpacitySlider').addEventListener('input', function e() { swStyle.fillOpacity = escapeQuotes(this.value); setFillColor(swStyle.fillColor); @@ -431,6 +567,12 @@ const Stylewindow = function Stylewindow(optOptions = {}) { styleSelectedFeatures(); }); + document.getElementById('o-draw-style-backgroundFillOpacitySlider').addEventListener('input', function e() { + swStyle.backgroundFillOpacity = escapeQuotes(this.value); + setBackgroundFillColor(swStyle.backgroundFillColor, escapeQuotes(this.value)); + styleSelectedFeatures(); + }); + document.getElementById('o-draw-style-strokeWidthSlider').addEventListener('input', function e() { swStyle.strokeWidth = escapeQuotes(this.value); styleSelectedFeatures(); @@ -441,6 +583,22 @@ const Stylewindow = function Stylewindow(optOptions = {}) { styleSelectedFeatures(); }); + document.getElementById('o-draw-style-backgroundStrokeWidthSlider').addEventListener('input', function e() { + swStyle.backgroundStrokeWidth = escapeQuotes(this.value); + styleSelectedFeatures(); + }); + + document.getElementById('o-draw-style-backgroundStrokeType').addEventListener('change', function e() { + swStyle.backgroundStrokeType = escapeQuotes(this.value); + styleSelectedFeatures(); + }); + + document.getElementById('o-draw-style-backgroundStrokeOpacitySlider').addEventListener('input', function e() { + swStyle.backgroundStrokeOpacity = escapeQuotes(this.value); + setBackgroundStrokeColor(swStyle.backgroundStrokeColor); + styleSelectedFeatures(); + }); + document.getElementById('o-draw-style-pointType').addEventListener('change', function e() { swStyle.pointType = escapeQuotes(this.value); styleSelectedFeatures(); @@ -470,6 +628,16 @@ const Stylewindow = function Stylewindow(optOptions = {}) { swStyle.textSize = escapeQuotes(this.value); styleSelectedFeatures(); }); + + document.getElementById('o-draw-style-rotationSlider').addEventListener('input', function e() { + swStyle.objRotation = escapeQuotes(this.value); + styleSelectedFeatures(); + }); + + document.getElementById('o-draw-style-paddingSlider').addEventListener('input', function e() { + swStyle.paddingText = escapeQuotes(this.value); + styleSelectedFeatures(); + }); } annotationField = optOptions.annotation || 'annotation';