qwc2
Version:
QGIS Web Client
262 lines (260 loc) • 12.8 kB
JavaScript
function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
function _classCallCheck(a, n) { if (!(a instanceof n)) throw new TypeError("Cannot call a class as a function"); }
function _defineProperties(e, r) { for (var t = 0; t < r.length; t++) { var o = r[t]; o.enumerable = o.enumerable || !1, o.configurable = !0, "value" in o && (o.writable = !0), Object.defineProperty(e, _toPropertyKey(o.key), o); } }
function _createClass(e, r, t) { return r && _defineProperties(e.prototype, r), t && _defineProperties(e, t), Object.defineProperty(e, "prototype", { writable: !1 }), e; }
function _callSuper(t, o, e) { return o = _getPrototypeOf(o), _possibleConstructorReturn(t, _isNativeReflectConstruct() ? Reflect.construct(o, e || [], _getPrototypeOf(t).constructor) : o.apply(t, e)); }
function _possibleConstructorReturn(t, e) { if (e && ("object" == _typeof(e) || "function" == typeof e)) return e; if (void 0 !== e) throw new TypeError("Derived constructors may only return object or undefined"); return _assertThisInitialized(t); }
function _assertThisInitialized(e) { if (void 0 === e) throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); return e; }
function _isNativeReflectConstruct() { try { var t = !Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); } catch (t) {} return (_isNativeReflectConstruct = function _isNativeReflectConstruct() { return !!t; })(); }
function _getPrototypeOf(t) { return _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf.bind() : function (t) { return t.__proto__ || Object.getPrototypeOf(t); }, _getPrototypeOf(t); }
function _inherits(t, e) { if ("function" != typeof e && null !== e) throw new TypeError("Super expression must either be null or a function"); t.prototype = Object.create(e && e.prototype, { constructor: { value: t, writable: !0, configurable: !0 } }), Object.defineProperty(t, "prototype", { writable: !1 }), e && _setPrototypeOf(t, e); }
function _setPrototypeOf(t, e) { return _setPrototypeOf = Object.setPrototypeOf ? Object.setPrototypeOf.bind() : function (t, e) { return t.__proto__ = e, t; }, _setPrototypeOf(t, e); }
function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : i + ""; }
function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
/**
* Copyright 2024 Sourcepole AG
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree.
*/
import React from 'react';
import { connect } from 'react-redux';
import isEmpty from 'lodash.isempty';
import PropTypes from 'prop-types';
import { setCurrentTask } from '../actions/task';
import ResizeableWindow from '../components/ResizeableWindow';
import { Image } from '../components/widgets/Primitives';
import LayerUtils from '../utils/LayerUtils';
import LocaleUtils from '../utils/LocaleUtils';
import MapUtils from '../utils/MapUtils';
import './style/MapLegend.css';
/**
* Displays the map legend in a floating dialog.
*
* The user can toggle whether to display only layers which are enabled, visible in the current extent and/or visible at the current scale.
*
* See https://docs.qgis.org/3.28/en/docs/server_manual/services/wms.html#wms-getlegendgraphic for supported extra legend params.
*/
var MapLegend = /*#__PURE__*/function (_React$Component) {
function MapLegend(props) {
var _this;
_classCallCheck(this, MapLegend);
_this = _callSuper(this, MapLegend, [props]);
_defineProperty(_this, "state", {
onlyVisibleLegend: false,
bboxDependentLegend: false,
scaleDependentLegend: false,
visible: false
});
_defineProperty(_this, "onClose", function () {
_this.setState({
visible: false
});
});
_defineProperty(_this, "printLayerLegend", function (layer, sublayer, mapScale) {
var isCategorized = (sublayer.sublayers || []).find(function (entry) {
return entry.category_sublayer === true;
});
if (_this.props.excludeLayers.includes(sublayer.name)) {
return null;
} else if (sublayer.sublayers && !isCategorized && (!_this.state.onlyVisibleLegend || sublayer.visibility)) {
if (_this.props.addGroupTitles) {
var children = sublayer.sublayers.map(function (subsublayer) {
return _this.printLayerLegend(layer, subsublayer, mapScale);
}).filter(function (x) {
return x;
});
if (isEmpty(children)) {
return null;
} else {
return /*#__PURE__*/React.createElement("div", {
className: "map-legend-group",
key: sublayer.name
}, /*#__PURE__*/React.createElement("div", {
className: "map-legend-group-title"
}, sublayer.title || sublayer.name), /*#__PURE__*/React.createElement("div", {
className: "map-legend-group-entries"
}, sublayer.sublayers.map(function (subsublayer) {
return _this.printLayerLegend(layer, subsublayer, mapScale);
})));
}
} else {
return sublayer.sublayers.map(function (subsublayer) {
return _this.printLayerLegend(layer, subsublayer, mapScale);
});
}
} else {
if (_this.state.onlyVisibleLegend && !sublayer.visibility) {
return null;
}
if ((_this.state.onlyVisibleLegend || _this.state.scaleDependentLegend) && !LayerUtils.layerScaleInRange(sublayer, mapScale)) {
return null;
}
var request = LayerUtils.getLegendUrl(layer, sublayer, mapScale, _this.props.map, _this.state.bboxDependentLegend, _this.state.scaleDependentLegend, _this.props.extraLegendParameters);
return request ? /*#__PURE__*/React.createElement("div", {
className: "map-legend-legend-entry",
key: sublayer.name
}, /*#__PURE__*/React.createElement("div", null, _this.props.addLayerTitles && !sublayer.category_sublayer ? /*#__PURE__*/React.createElement("div", {
className: "map-legend-entry-title"
}, sublayer.title || sublayer.name) : null, /*#__PURE__*/React.createElement("div", {
className: "map-legend-entry-image"
}, /*#__PURE__*/React.createElement(Image, {
src: request
})))) : null;
}
});
_this.state.onlyVisibleLegend = props.onlyVisibleLegend;
_this.state.bboxDependentLegend = props.bboxDependentLegend;
_this.state.scaleDependentLegend = props.scaleDependentLegend;
return _this;
}
_inherits(MapLegend, _React$Component);
return _createClass(MapLegend, [{
key: "componentDidUpdate",
value: function componentDidUpdate(prevProps) {
if (this.props.active && !prevProps.active) {
this.setState({
visible: true
});
// Clear task immediately, visibility is stored as state
this.props.setCurrentTask(null);
}
}
}, {
key: "render",
value: function render() {
var _this2 = this;
if (!this.state.visible && !this.props.lockedWindow) {
return null;
}
var mapScale = MapUtils.computeForZoom(this.props.map.scales, this.props.map.zoom);
var extraControls = [{
icon: "eye",
callback: function callback() {
return _this2.setState(function (state) {
return {
onlyVisibleLegend: !state.onlyVisibleLegend
};
});
},
active: this.state.onlyVisibleLegend,
title: LocaleUtils.tr("maplegend.onlyvisible")
}, {
icon: "box",
callback: function callback() {
return _this2.setState(function (state) {
return {
bboxDependentLegend: !state.bboxDependentLegend
};
});
},
active: this.state.bboxDependentLegend,
title: LocaleUtils.tr("maplegend.bboxdependent")
}, {
icon: "scale",
callback: function callback() {
return _this2.setState(function (state) {
return {
scaleDependentLegend: !state.scaleDependentLegend
};
});
},
active: this.state.scaleDependentLegend,
title: LocaleUtils.tr("maplegend.scaledependent")
}];
return /*#__PURE__*/React.createElement(ResizeableWindow, {
dockable: this.props.lockedWindow ? false : this.props.geometry.side,
extraControls: extraControls,
icon: "list-alt",
initialHeight: this.props.geometry.initialHeight,
initialWidth: this.props.geometry.initialWidth,
initialX: this.props.geometry.initialX,
initialY: this.props.geometry.initialY,
initiallyDocked: this.props.geometry.initiallyDocked,
maximizeable: false,
onClose: this.props.lockedWindow ? null : this.onClose,
title: LocaleUtils.tr("maplegend.windowtitle")
}, /*#__PURE__*/React.createElement("div", {
className: "map-legend"
}, this.props.layers.map(function (layer) {
if (_this2.state.onlyVisibleLegend && !layer.visibility) {
return null;
} else if (layer.legendUrl) {
return _this2.printLayerLegend(layer, layer, mapScale);
} else if (layer.color) {
return /*#__PURE__*/React.createElement("div", {
className: "map-legend-legend-entry",
key: layer.name
}, /*#__PURE__*/React.createElement("span", {
className: "map-legend-color-box",
style: {
backgroundColor: layer.color
}
}), /*#__PURE__*/React.createElement("span", {
className: "map-legend-entry-title"
}, layer.title || layer.name));
} else {
return null;
}
})));
}
}]);
}(React.Component);
_defineProperty(MapLegend, "propTypes", {
active: PropTypes.bool,
/** Whether to add group titles to the legend. */
addGroupTitles: PropTypes.bool,
/** Whether to add layer titles to the legend. Note that often the legend image itself already contains the layer title. */
addLayerTitles: PropTypes.bool,
/** Whether to display a BBOX-dependent legend by default. */
bboxDependentLegend: PropTypes.bool,
/** List of layernames to exclude from the legend. */
excludeLayers: PropTypes.array,
/** Extra parameters to add to the GetLegendGraphics request. */
extraLegendParameters: PropTypes.string,
/** Default window geometry with size, position and docking status. A locked window is not closeable and not resizeable. Positive position values (including '0') are related to top (InitialY) and left (InitialX), negative values (including '-0') to bottom (InitialY) and right (InitialX). */
geometry: PropTypes.shape({
initialWidth: PropTypes.number,
initialHeight: PropTypes.number,
initialX: PropTypes.number,
initialY: PropTypes.number,
initiallyDocked: PropTypes.bool,
side: PropTypes.string
}),
layers: PropTypes.array,
/** Whether the legend window is locked (always visible, not moveable or closeable). Set position and size via `geometry`. */
lockedWindow: PropTypes.bool,
map: PropTypes.object,
/** Whether to only include enabled layers in the legend by default. */
onlyVisibleLegend: PropTypes.bool,
/** Whether to display a scale-dependent legend by default. */
scaleDependentLegend: PropTypes.bool,
setCurrentTask: PropTypes.func
});
_defineProperty(MapLegend, "defaultProps", {
addGroupTitles: false,
addLayerTitles: false,
bboxDependentLegend: false,
excludeLayers: [],
onlyVisibleLegend: false,
scaleDependentLegend: false,
geometry: {
initialWidth: 320,
initialHeight: 320,
initialX: 0,
initialY: 0,
initiallyDocked: false,
side: 'left'
}
});
export default connect(function (state) {
return {
active: state.task.id === "MapLegend",
layers: state.layers.flat,
map: state.map
};
}, {
setCurrentTask: setCurrentTask
})(MapLegend);