@panoramax/web-viewer 3.2.3-develop-d7e5a16d → 3.2.3-develop-f9c0224b
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.gitlab-ci.yml +5 -0
- package/CHANGELOG.md +19 -0
- package/CODE_OF_CONDUCT.md +1 -1
- package/README.md +1 -1
- package/build/editor.html +10 -1
- package/build/index.css +2 -2
- package/build/index.css.map +1 -1
- package/build/index.html +1 -1
- package/build/index.js +1682 -5
- package/build/index.js.map +1 -1
- package/build/map.html +1 -1
- package/build/viewer.html +10 -1
- package/build/widgets.html +1 -0
- package/config/jest/mocks.js +172 -0
- package/config/paths.js +1 -0
- package/config/webpack.config.js +26 -0
- package/docs/03_URL_settings.md +3 -11
- package/docs/05_Compatibility.md +59 -76
- package/docs/09_Develop.md +30 -11
- package/docs/90_Releases.md +2 -2
- package/docs/images/class_diagram.drawio +28 -28
- package/docs/images/class_diagram.jpg +0 -0
- package/docs/index.md +112 -0
- package/docs/reference/components/core/Basic.md +153 -0
- package/docs/reference/components/core/CoverageMap.md +160 -0
- package/docs/reference/components/core/Editor.md +172 -0
- package/docs/reference/components/core/Viewer.md +288 -0
- package/docs/reference/components/layout/CorneredGrid.md +29 -0
- package/docs/reference/components/layout/Mini.md +45 -0
- package/docs/reference/components/menus/MapBackground.md +32 -0
- package/docs/reference/components/menus/MapFilters.md +15 -0
- package/docs/reference/components/menus/MapLayers.md +15 -0
- package/docs/reference/components/menus/MapLegend.md +15 -0
- package/docs/reference/components/menus/PictureLegend.md +15 -0
- package/docs/reference/components/menus/PictureMetadata.md +15 -0
- package/docs/reference/components/menus/PlayerOptions.md +15 -0
- package/docs/reference/components/menus/QualityScoreDoc.md +15 -0
- package/docs/reference/components/menus/ReportForm.md +15 -0
- package/docs/reference/components/menus/ShareMenu.md +15 -0
- package/docs/reference/components/ui/Button.md +39 -0
- package/docs/reference/components/ui/ButtonGroup.md +36 -0
- package/docs/reference/components/ui/CopyButton.md +35 -0
- package/docs/reference/components/ui/Grade.md +32 -0
- package/docs/reference/components/ui/LinkButton.md +44 -0
- package/docs/reference/components/ui/Loader.md +54 -0
- package/docs/reference/components/ui/Map.md +214 -0
- package/docs/reference/components/ui/MapMore.md +233 -0
- package/docs/reference/components/ui/Photo.md +369 -0
- package/docs/reference/components/ui/Popup.md +56 -0
- package/docs/reference/components/ui/QualityScore.md +45 -0
- package/docs/reference/components/ui/SearchBar.md +63 -0
- package/docs/reference/components/ui/TogglableGroup.md +39 -0
- package/docs/reference/components/ui/widgets/GeoSearch.md +32 -0
- package/docs/reference/components/ui/widgets/Legend.md +32 -0
- package/docs/reference/components/ui/widgets/MapFiltersButton.md +33 -0
- package/docs/reference/components/ui/widgets/MapLayersButton.md +15 -0
- package/docs/reference/components/ui/widgets/Player.md +32 -0
- package/docs/reference/components/ui/widgets/Share.md +15 -0
- package/docs/reference/components/ui/widgets/Zoom.md +15 -0
- package/docs/reference/utils/API.md +311 -0
- package/docs/reference/utils/InitParameters.md +67 -0
- package/docs/reference/utils/URLHandler.md +102 -0
- package/docs/reference.md +73 -0
- package/docs/shortcuts.md +11 -0
- package/docs/tutorials/aerial_imagery.md +19 -0
- package/docs/tutorials/authentication.md +10 -0
- package/docs/tutorials/custom_widgets.md +64 -0
- package/docs/tutorials/map_style.md +27 -0
- package/docs/tutorials/migrate_v4.md +122 -0
- package/docs/tutorials/synced_coverage.md +42 -0
- package/mkdocs.yml +60 -5
- package/package.json +10 -7
- package/public/editor.html +21 -29
- package/public/index.html +3 -3
- package/public/map.html +19 -18
- package/public/viewer.html +18 -24
- package/public/widgets.html +265 -0
- package/scripts/doc.js +77 -0
- package/src/components/core/Basic.css +44 -0
- package/src/components/core/Basic.js +258 -0
- package/src/components/core/CoverageMap.css +9 -0
- package/src/components/core/CoverageMap.js +105 -0
- package/src/components/core/Editor.css +23 -0
- package/src/components/core/Editor.js +354 -0
- package/src/components/core/Viewer.css +109 -0
- package/src/components/core/Viewer.js +707 -0
- package/src/components/core/index.js +11 -0
- package/src/components/index.js +13 -0
- package/src/components/layout/CorneredGrid.js +109 -0
- package/src/components/layout/Mini.js +117 -0
- package/src/components/layout/index.js +7 -0
- package/src/components/menus/MapBackground.js +106 -0
- package/src/components/menus/MapFilters.js +386 -0
- package/src/components/menus/MapLayers.js +143 -0
- package/src/components/menus/MapLegend.js +54 -0
- package/src/components/menus/PictureLegend.js +103 -0
- package/src/components/menus/PictureMetadata.js +188 -0
- package/src/components/menus/PlayerOptions.js +96 -0
- package/src/components/menus/QualityScoreDoc.js +36 -0
- package/src/components/menus/ReportForm.js +133 -0
- package/src/components/menus/Share.js +228 -0
- package/src/components/menus/index.js +15 -0
- package/src/components/styles.js +365 -0
- package/src/components/ui/Button.js +75 -0
- package/src/components/ui/ButtonGroup.css +49 -0
- package/src/components/ui/ButtonGroup.js +68 -0
- package/src/components/ui/CopyButton.js +71 -0
- package/src/components/ui/Grade.js +54 -0
- package/src/components/ui/LinkButton.js +68 -0
- package/src/components/ui/Loader.js +188 -0
- package/src/components/{Map.css → ui/Map.css} +5 -17
- package/src/components/{Map.js → ui/Map.js} +114 -138
- package/src/components/ui/MapMore.js +324 -0
- package/src/components/{Photo.css → ui/Photo.css} +6 -6
- package/src/components/{Photo.js → ui/Photo.js} +279 -90
- package/src/components/ui/Popup.js +145 -0
- package/src/components/ui/QualityScore.js +152 -0
- package/src/components/ui/SearchBar.js +363 -0
- package/src/components/ui/TogglableGroup.js +162 -0
- package/src/components/ui/index.js +20 -0
- package/src/components/ui/widgets/GeoSearch.css +21 -0
- package/src/components/ui/widgets/GeoSearch.js +139 -0
- package/src/components/ui/widgets/Legend.js +51 -0
- package/src/components/ui/widgets/MapFiltersButton.js +104 -0
- package/src/components/ui/widgets/MapLayersButton.js +79 -0
- package/src/components/ui/widgets/Player.css +7 -0
- package/src/components/ui/widgets/Player.js +148 -0
- package/src/components/ui/widgets/Share.js +30 -0
- package/src/components/ui/widgets/Zoom.js +82 -0
- package/src/components/ui/widgets/index.js +12 -0
- package/src/img/panoramax.svg +13 -0
- package/src/img/switch_big.svg +20 -10
- package/src/index.js +6 -9
- package/src/translations/da.json +1 -1
- package/src/translations/de.json +1 -1
- package/src/translations/en.json +5 -3
- package/src/translations/eo.json +1 -1
- package/src/translations/es.json +1 -1
- package/src/translations/fr.json +5 -3
- package/src/translations/hu.json +1 -1
- package/src/translations/it.json +1 -1
- package/src/translations/ja.json +1 -1
- package/src/translations/nl.json +1 -1
- package/src/translations/pl.json +1 -1
- package/src/translations/sv.json +1 -1
- package/src/translations/zh_Hant.json +1 -1
- package/src/utils/API.js +74 -42
- package/src/utils/InitParameters.js +354 -0
- package/src/utils/URLHandler.js +364 -0
- package/src/utils/geocoder.js +116 -0
- package/src/utils/{I18n.js → i18n.js} +3 -1
- package/src/utils/index.js +11 -0
- package/src/utils/{Map.js → map.js} +216 -80
- package/src/utils/picture.js +433 -0
- package/src/utils/utils.js +315 -0
- package/src/utils/widgets.js +93 -0
- package/tests/components/ui/CopyButton.test.js +52 -0
- package/tests/components/ui/Loader.test.js +54 -0
- package/tests/components/{Map.test.js → ui/Map.test.js} +19 -61
- package/tests/components/{Photo.test.js → ui/Photo.test.js} +89 -57
- package/tests/components/ui/Popup.test.js +24 -0
- package/tests/components/ui/QualityScore.test.js +17 -0
- package/tests/components/ui/SearchBar.test.js +107 -0
- package/tests/components/ui/__snapshots__/CopyButton.test.js.snap +34 -0
- package/tests/components/ui/__snapshots__/Loader.test.js.snap +56 -0
- package/tests/components/{__snapshots__ → ui/__snapshots__}/Map.test.js.snap +11 -38
- package/tests/components/{__snapshots__ → ui/__snapshots__}/Photo.test.js.snap +57 -4
- package/tests/components/ui/__snapshots__/Popup.test.js.snap +29 -0
- package/tests/components/ui/__snapshots__/QualityScore.test.js.snap +11 -0
- package/tests/components/ui/__snapshots__/SearchBar.test.js.snap +65 -0
- package/tests/utils/API.test.js +1 -14
- package/tests/utils/InitParameters.test.js +485 -0
- package/tests/utils/URLHandler.test.js +350 -0
- package/tests/utils/__snapshots__/URLHandler.test.js.snap +21 -0
- package/tests/utils/__snapshots__/picture.test.js.snap +315 -0
- package/tests/utils/__snapshots__/widgets.test.js.snap +19 -0
- package/tests/utils/geocoder.test.js +37 -0
- package/tests/utils/{I18n.test.js → i18n.test.js} +1 -1
- package/tests/utils/map.test.js +67 -0
- package/tests/utils/picture.test.js +745 -0
- package/tests/utils/utils.test.js +288 -0
- package/tests/utils/widgets.test.js +90 -0
- package/docs/01_Start.md +0 -149
- package/docs/02_Usage.md +0 -831
- package/docs/04_Advanced_examples.md +0 -216
- package/src/Editor.css +0 -37
- package/src/Editor.js +0 -361
- package/src/StandaloneMap.js +0 -114
- package/src/Viewer.css +0 -203
- package/src/Viewer.js +0 -1246
- package/src/components/CoreView.css +0 -70
- package/src/components/CoreView.js +0 -175
- package/src/components/Loader.css +0 -74
- package/src/components/Loader.js +0 -120
- package/src/utils/Exif.js +0 -193
- package/src/utils/Utils.js +0 -631
- package/src/utils/Widgets.js +0 -562
- package/src/viewer/URLHash.js +0 -469
- package/src/viewer/Widgets.css +0 -880
- package/src/viewer/Widgets.js +0 -1470
- package/tests/Editor.test.js +0 -126
- package/tests/StandaloneMap.test.js +0 -45
- package/tests/Viewer.test.js +0 -366
- package/tests/__snapshots__/Editor.test.js.snap +0 -298
- package/tests/__snapshots__/StandaloneMap.test.js.snap +0 -30
- package/tests/__snapshots__/Viewer.test.js.snap +0 -195
- package/tests/components/CoreView.test.js +0 -92
- package/tests/components/Loader.test.js +0 -38
- package/tests/components/__snapshots__/Loader.test.js.snap +0 -15
- package/tests/utils/Exif.test.js +0 -124
- package/tests/utils/Map.test.js +0 -113
- package/tests/utils/Utils.test.js +0 -300
- package/tests/utils/Widgets.test.js +0 -107
- package/tests/utils/__snapshots__/Exif.test.js.snap +0 -43
- package/tests/utils/__snapshots__/Utils.test.js.snap +0 -41
- package/tests/utils/__snapshots__/Widgets.test.js.snap +0 -44
- package/tests/viewer/URLHash.test.js +0 -559
- package/tests/viewer/Widgets.test.js +0 -127
- package/tests/viewer/__snapshots__/URLHash.test.js.snap +0 -108
- package/tests/viewer/__snapshots__/Widgets.test.js.snap +0 -403
- /package/tests/utils/__snapshots__/{Map.test.js.snap → geocoder.test.js.snap} +0 -0
|
@@ -1,14 +1,13 @@
|
|
|
1
1
|
import "./Map.css";
|
|
2
2
|
import {
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
} from "
|
|
7
|
-
import
|
|
8
|
-
import
|
|
9
|
-
import
|
|
10
|
-
import
|
|
11
|
-
import Arrow360SVG from "../img/arrow_360.svg";
|
|
3
|
+
VECTOR_STYLES, TILES_PICTURES_ZOOM, getThumbGif, RASTER_LAYER_ID, combineStyles,
|
|
4
|
+
getMissingLayerStyles, isLabelLayer, getUserLayerId, getUserSourceId,
|
|
5
|
+
} from "../../utils/map";
|
|
6
|
+
import { COLORS } from "../../utils/utils";
|
|
7
|
+
import MarkerBaseSVG from "../../img/marker.svg";
|
|
8
|
+
import MarkerSelectedSVG from "../../img/marker_blue.svg";
|
|
9
|
+
import ArrowFlatSVG from "../../img/arrow_flat.svg";
|
|
10
|
+
import Arrow360SVG from "../../img/arrow_360.svg";
|
|
12
11
|
|
|
13
12
|
// MapLibre imports
|
|
14
13
|
import "maplibre-gl/dist/maplibre-gl.css";
|
|
@@ -38,13 +37,25 @@ const filterMapLibreOptions = opts => Object.fromEntries(Object.entries(opts).fi
|
|
|
38
37
|
*
|
|
39
38
|
* Note that all functions of [MapLibre GL JS class Map](https://maplibre.org/maplibre-gl-js/docs/API/classes/Map/) are also available.
|
|
40
39
|
*
|
|
41
|
-
*
|
|
40
|
+
* A more complete version of Map (with filters & themes) is available through [MapMore class](#Panoramax.components.ui.MapMore)
|
|
41
|
+
*
|
|
42
|
+
* ⚠️ This class doesn't inherit from [EventTarget](https://developer.mozilla.org/fr/docs/Web/API/EventTarget), so it doesn't have `addEventListener` and `dispatchEvent` functions.
|
|
43
|
+
* It uses instead [`on`](https://maplibre.org/maplibre-gl-js/docs/API/classes/Map/#on) and `fire` functions from MapLibre Map class.
|
|
44
|
+
* `fire` function doesn't take directly [`Event`](https://developer.mozilla.org/fr/docs/Web/API/Event) objects, but a string and object data.
|
|
45
|
+
* @class Panoramax.components.ui.Map
|
|
46
|
+
* @extends [maplibregl.Map](https://maplibre.org/maplibre-gl-js/docs/API/classes/Map/)
|
|
47
|
+
* @param {Panoramax.components.core.Basic} parent The parent view
|
|
42
48
|
* @param {Element} container The DOM element to create into
|
|
43
49
|
* @param {object} [options] The map options (any of [MapLibre GL settings](https://maplibre.org/maplibre-gl-js-docs/api/map/#map-parameters) or any supplementary option defined here)
|
|
44
50
|
* @param {object} [options.raster] The MapLibre raster source for aerial background. This must be a JSON object following [MapLibre raster source definition](https://maplibre.org/maplibre-style-spec/sources/#raster).
|
|
45
|
-
* @param {string} [options.background] Choose default map background to display (streets or aerial, if raster aerial background available). Defaults to street.
|
|
46
|
-
* @
|
|
47
|
-
* @
|
|
51
|
+
* @param {string} [options.background=streets] Choose default map background to display (streets or aerial, if raster aerial background available). Defaults to street.
|
|
52
|
+
* @fires Panoramax.components.ui.Map#background-changed
|
|
53
|
+
* @fires Panoramax.components.ui.Map#users-changed
|
|
54
|
+
* @fires Panoramax.components.ui.Map#sequence-hover
|
|
55
|
+
* @fires Panoramax.components.ui.Map#sequence-click
|
|
56
|
+
* @fires Panoramax.components.ui.Map#picture-click
|
|
57
|
+
* @example
|
|
58
|
+
* const map = new Panoramax.components.ui.Map(viewer, mapNode, {center: {lat: 48.7, lng: -1.7}});
|
|
48
59
|
*/
|
|
49
60
|
export default class Map extends maplibregl.Map {
|
|
50
61
|
constructor(parent, container, options = {}) {
|
|
@@ -59,16 +70,18 @@ export default class Map extends maplibregl.Map {
|
|
|
59
70
|
pitchWithRotate: false,
|
|
60
71
|
touchZoomRotate: true,
|
|
61
72
|
touchPitch: false,
|
|
73
|
+
doubleClickZoom: false,
|
|
62
74
|
preserveDrawingBuffer: !parent.isWidthSmall(),
|
|
63
|
-
transformRequest: parent.
|
|
75
|
+
transformRequest: parent.api._getMapRequestTransform(),
|
|
64
76
|
locale: parent._t.maplibre,
|
|
77
|
+
hash: false,
|
|
65
78
|
...filterMapLibreOptions(options)
|
|
66
79
|
});
|
|
67
80
|
this._loadMarkerImages();
|
|
68
81
|
|
|
69
82
|
this._parent = parent;
|
|
70
83
|
this._options = options;
|
|
71
|
-
this.getContainer().classList.add("
|
|
84
|
+
this.getContainer().classList.add("pnx-map");
|
|
72
85
|
|
|
73
86
|
// Disable touch rotate
|
|
74
87
|
if(options.touchZoomRotate === undefined) {
|
|
@@ -83,7 +96,6 @@ export default class Map extends maplibregl.Map {
|
|
|
83
96
|
this._attribution = new maplibregl.AttributionControl({ compact: false });
|
|
84
97
|
this.addControl(this._attribution);
|
|
85
98
|
|
|
86
|
-
this._initGeocoder();
|
|
87
99
|
this._initMapPosition();
|
|
88
100
|
|
|
89
101
|
// Widgets and markers
|
|
@@ -97,16 +109,13 @@ export default class Map extends maplibregl.Map {
|
|
|
97
109
|
// Sequences and pictures per users
|
|
98
110
|
this._userLayers = new Set();
|
|
99
111
|
|
|
100
|
-
// Hover event
|
|
101
|
-
this.on("mousemove", "sequences", this._onSequenceHover.bind(this));
|
|
102
|
-
|
|
103
112
|
// Parent selection
|
|
104
113
|
this._parent.addEventListener("select", this.reloadLayersStyles.bind(this));
|
|
105
114
|
|
|
106
115
|
// Timeout for initial loading
|
|
107
116
|
setTimeout(() => {
|
|
108
|
-
if(!this.loaded() && this._parent.
|
|
109
|
-
this._parent.
|
|
117
|
+
if(!this.loaded() && this._parent.loader.isVisible()) {
|
|
118
|
+
this._parent.loader.dismiss({}, this._parent._t.map.slow_loading, () => {});
|
|
110
119
|
}
|
|
111
120
|
}, 15000);
|
|
112
121
|
|
|
@@ -118,12 +127,13 @@ export default class Map extends maplibregl.Map {
|
|
|
118
127
|
*/
|
|
119
128
|
async _postLoad() {
|
|
120
129
|
this.resize();
|
|
121
|
-
await this.setVisibleUsers(this._parent.
|
|
130
|
+
await this.setVisibleUsers(this._parent.users);
|
|
122
131
|
this.reloadLayersStyles();
|
|
123
132
|
}
|
|
124
133
|
|
|
125
134
|
/**
|
|
126
135
|
* Destroy any form of life in this component
|
|
136
|
+
* @memberof Panoramax.components.ui.Map#
|
|
127
137
|
*/
|
|
128
138
|
destroy() {
|
|
129
139
|
this.remove();
|
|
@@ -140,6 +150,7 @@ export default class Map extends maplibregl.Map {
|
|
|
140
150
|
/**
|
|
141
151
|
* Helper to know when enough map background and Panoramax tiles are loaded for a proper display.
|
|
142
152
|
* @returns {Promise} Resolves when enough is loaded
|
|
153
|
+
* @memberof Panoramax.components.ui.Map#
|
|
143
154
|
*/
|
|
144
155
|
waitForEnoughMapLoaded() {
|
|
145
156
|
return new Promise((resolve) => {
|
|
@@ -173,7 +184,7 @@ export default class Map extends maplibregl.Map {
|
|
|
173
184
|
};
|
|
174
185
|
|
|
175
186
|
const checkEnoughLoaded = () => {
|
|
176
|
-
if(nbLoadedBgTiles / nbBgTiles >= 0.75 && nbLoadedFgTiles / nbFgTiles >= 0.75) {
|
|
187
|
+
if(nbLoadedBgTiles / nbBgTiles >= 0.75 && (nbFgTiles === 0 || nbLoadedFgTiles / nbFgTiles >= 0.75)) {
|
|
177
188
|
this.off("sourcedata", onSourceData);
|
|
178
189
|
this.off("sourcedataloading", onSourceDataLoading);
|
|
179
190
|
resolve();
|
|
@@ -188,6 +199,7 @@ export default class Map extends maplibregl.Map {
|
|
|
188
199
|
/**
|
|
189
200
|
* Sets map view based on returned API bbox (if no precise option given by user).
|
|
190
201
|
* @private
|
|
202
|
+
* @memberof Panoramax.components.ui.Map#
|
|
191
203
|
*/
|
|
192
204
|
_initMapPosition() {
|
|
193
205
|
if(
|
|
@@ -195,8 +207,8 @@ export default class Map extends maplibregl.Map {
|
|
|
195
207
|
&& (!this._options.zoom || this._options.zoom === 0)
|
|
196
208
|
&& (!this._options.hash)
|
|
197
209
|
) {
|
|
198
|
-
this._parent.
|
|
199
|
-
let bbox = this._parent?.
|
|
210
|
+
this._parent.onceAPIReady().then(() => {
|
|
211
|
+
let bbox = this._parent?.api?.getDataBbox();
|
|
200
212
|
if(bbox) {
|
|
201
213
|
try {
|
|
202
214
|
bbox = new maplibregl.LngLatBounds(bbox);
|
|
@@ -211,35 +223,16 @@ export default class Map extends maplibregl.Map {
|
|
|
211
223
|
}
|
|
212
224
|
}
|
|
213
225
|
|
|
214
|
-
/**
|
|
215
|
-
* Creates the geocoder search bar
|
|
216
|
-
* @private
|
|
217
|
-
*/
|
|
218
|
-
_initGeocoder() {
|
|
219
|
-
const engines = { "ban": forwardGeocodingBAN, "nominatim": forwardGeocodingNominatim };
|
|
220
|
-
const engine = this._options?.geocoder?.engine || "nominatim";
|
|
221
|
-
this.geocoder = engines[engine];
|
|
222
|
-
this._geolocate = new maplibregl.GeolocateControl({
|
|
223
|
-
positionOptions: {
|
|
224
|
-
enableHighAccuracy: true,
|
|
225
|
-
timeout: 60000, // Max 1 minute for first position
|
|
226
|
-
maximumAge: 300000, // Accepts 5 minutes old position
|
|
227
|
-
},
|
|
228
|
-
showAccuracyCircle: true,
|
|
229
|
-
showUserLocation: true,
|
|
230
|
-
trackUserLocation: true,
|
|
231
|
-
}).onAdd(this);
|
|
232
|
-
}
|
|
233
|
-
|
|
234
226
|
/**
|
|
235
227
|
* Load markers into map for use in map layers.
|
|
236
228
|
* @private
|
|
229
|
+
* @memberof Panoramax.components.ui.Map#
|
|
237
230
|
*/
|
|
238
231
|
_loadMarkerImages() {
|
|
239
232
|
[
|
|
240
|
-
{ id: "
|
|
241
|
-
{ id: "
|
|
242
|
-
{ id: "
|
|
233
|
+
{ id: "pnx-marker", img: MarkerBaseSVG },
|
|
234
|
+
{ id: "pnx-arrow-flat", img: ArrowFlatSVG },
|
|
235
|
+
{ id: "pnx-arrow-360", img: Arrow360SVG },
|
|
243
236
|
].forEach(m => {
|
|
244
237
|
const img = new Image(64, 64);
|
|
245
238
|
img.onload = () => this.addImage(m.id, img);
|
|
@@ -250,6 +243,7 @@ export default class Map extends maplibregl.Map {
|
|
|
250
243
|
/**
|
|
251
244
|
* Is Quality Score available in vector tiles ?
|
|
252
245
|
* @private
|
|
246
|
+
* @memberof Panoramax.components.ui.Map#
|
|
253
247
|
*/
|
|
254
248
|
_hasQualityScore() {
|
|
255
249
|
const fields = this.getStyle()?.metadata?.["panoramax:fields"] || {};
|
|
@@ -259,6 +253,7 @@ export default class Map extends maplibregl.Map {
|
|
|
259
253
|
/**
|
|
260
254
|
* Are 360/flat pictures stats available in vector tiles for grid layer ?
|
|
261
255
|
* @private
|
|
256
|
+
* @memberof Panoramax.components.ui.Map#
|
|
262
257
|
*/
|
|
263
258
|
_hasGridStats() {
|
|
264
259
|
const fields = this.getStyle()?.metadata?.["panoramax:fields"] || {};
|
|
@@ -268,6 +263,7 @@ export default class Map extends maplibregl.Map {
|
|
|
268
263
|
|
|
269
264
|
/**
|
|
270
265
|
* Force refresh of vector tiles data
|
|
266
|
+
* @memberof Panoramax.components.ui.Map#
|
|
271
267
|
*/
|
|
272
268
|
reloadVectorTiles() {
|
|
273
269
|
[...this._userLayers].forEach(dl => {
|
|
@@ -279,6 +275,7 @@ export default class Map extends maplibregl.Map {
|
|
|
279
275
|
/**
|
|
280
276
|
* Check if map offers aerial imagery as well as streets rendering.
|
|
281
277
|
* @returns {boolean} True if aerial imagery is available for display
|
|
278
|
+
* @memberof Panoramax.components.ui.Map#
|
|
282
279
|
*/
|
|
283
280
|
hasTwoBackgrounds() {
|
|
284
281
|
return this.getLayer(RASTER_LAYER_ID) !== undefined;
|
|
@@ -287,6 +284,7 @@ export default class Map extends maplibregl.Map {
|
|
|
287
284
|
/**
|
|
288
285
|
* Get the currently selected map background
|
|
289
286
|
* @returns {string} aerial or streets
|
|
287
|
+
* @memberof Panoramax.components.ui.Map#
|
|
290
288
|
*/
|
|
291
289
|
getBackground() {
|
|
292
290
|
if(!this.getLayer(RASTER_LAYER_ID)) {
|
|
@@ -300,6 +298,8 @@ export default class Map extends maplibregl.Map {
|
|
|
300
298
|
/**
|
|
301
299
|
* Change the shown background in map.
|
|
302
300
|
* @param {string} bg The new background to display (aerial or streets)
|
|
301
|
+
* @memberof Panoramax.components.ui.Map#
|
|
302
|
+
* @throws {Error} If not aerial imagery is available
|
|
303
303
|
*/
|
|
304
304
|
setBackground(bg) {
|
|
305
305
|
if(!this.getLayer(RASTER_LAYER_ID) && bg === "aerial") { throw new Error("No aerial imagery available"); }
|
|
@@ -309,20 +309,18 @@ export default class Map extends maplibregl.Map {
|
|
|
309
309
|
/**
|
|
310
310
|
* Event for map background changes
|
|
311
311
|
*
|
|
312
|
-
* @event
|
|
313
|
-
* @
|
|
314
|
-
* @
|
|
315
|
-
* @property {object} detail Event information
|
|
316
|
-
* @property {string} [detail.background] The new selected background (aerial, streets)
|
|
312
|
+
* @event Panoramax.components.ui.Map#background-changed
|
|
313
|
+
* @type {maplibregl.util.evented.Event}
|
|
314
|
+
* @property {string} [background] The new selected background (aerial, streets)
|
|
317
315
|
*/
|
|
318
|
-
|
|
319
|
-
this._parent.dispatchEvent(event);
|
|
316
|
+
this.fire("background-changed", { background: bg || "streets" });
|
|
320
317
|
}
|
|
321
318
|
}
|
|
322
319
|
|
|
323
320
|
/**
|
|
324
321
|
* Get the currently visible users
|
|
325
322
|
* @returns {string[]} List of visible users
|
|
323
|
+
* @memberof Panoramax.components.ui.Map#
|
|
326
324
|
*/
|
|
327
325
|
getVisibleUsers() {
|
|
328
326
|
return [...this._userLayers].filter(l => (
|
|
@@ -332,7 +330,7 @@ export default class Map extends maplibregl.Map {
|
|
|
332
330
|
|
|
333
331
|
/**
|
|
334
332
|
* Make given user layers visible on map, and hide all others (if any)
|
|
335
|
-
*
|
|
333
|
+
* @memberof Panoramax.components.ui.Map#
|
|
336
334
|
* @param {string|string[]} visibleIds The user layers IDs to display
|
|
337
335
|
*/
|
|
338
336
|
async setVisibleUsers(visibleIds = []) {
|
|
@@ -359,20 +357,18 @@ export default class Map extends maplibregl.Map {
|
|
|
359
357
|
/**
|
|
360
358
|
* Event for visible users changes
|
|
361
359
|
*
|
|
362
|
-
* @event
|
|
363
|
-
* @
|
|
364
|
-
* @
|
|
365
|
-
* @property {object} detail Event information
|
|
366
|
-
* @property {string[]} [detail.usersIds] The list of newly selected users
|
|
360
|
+
* @event Panoramax.components.ui.Map#users-changed
|
|
361
|
+
* @type {maplibregl.util.evented.Event}
|
|
362
|
+
* @property {string[]} [usersIds] The list of newly selected users
|
|
367
363
|
*/
|
|
368
|
-
|
|
369
|
-
this._parent.dispatchEvent(event);
|
|
364
|
+
this.fire("users-changed", { usersIds: visibleIds });
|
|
370
365
|
}
|
|
371
366
|
|
|
372
367
|
/**
|
|
373
368
|
* Filter the visible data content in all visible map layers
|
|
374
369
|
* @param {string} dataType sequences or pictures
|
|
375
370
|
* @param {object} filter The MapLibre GL filter rule to apply
|
|
371
|
+
* @memberof Panoramax.components.ui.Map#
|
|
376
372
|
*/
|
|
377
373
|
filterUserLayersContent(dataType, filter) {
|
|
378
374
|
[...this._userLayers].forEach(l => {
|
|
@@ -388,12 +384,13 @@ export default class Map extends maplibregl.Map {
|
|
|
388
384
|
|
|
389
385
|
/**
|
|
390
386
|
* Shows on map a picture position and heading.
|
|
391
|
-
*
|
|
387
|
+
* @memberof Panoramax.components.ui.Map#
|
|
392
388
|
* @param {number} lon The longitude
|
|
393
389
|
* @param {number} lat The latitude
|
|
394
390
|
* @param {number} heading The heading
|
|
391
|
+
* @param {boolean} [skipCenter=false] Set to true to avoid map centering on marker
|
|
395
392
|
*/
|
|
396
|
-
displayPictureMarker(lon, lat, heading) {
|
|
393
|
+
displayPictureMarker(lon, lat, heading, skipCenter = false) {
|
|
397
394
|
this._picMarkerPreview.remove();
|
|
398
395
|
|
|
399
396
|
// Show marker corresponding to selection
|
|
@@ -411,7 +408,7 @@ export default class Map extends maplibregl.Map {
|
|
|
411
408
|
this.reloadLayersStyles();
|
|
412
409
|
|
|
413
410
|
// Move map to picture coordinates
|
|
414
|
-
if(lon !== undefined && lat !== undefined) {
|
|
411
|
+
if(!skipCenter && lon !== undefined && lat !== undefined) {
|
|
415
412
|
this.flyTo({
|
|
416
413
|
center: [lon, lat],
|
|
417
414
|
zoom: this.getZoom() < TILES_PICTURES_ZOOM+2 ? TILES_PICTURES_ZOOM+2 : this.getZoom(),
|
|
@@ -423,6 +420,7 @@ export default class Map extends maplibregl.Map {
|
|
|
423
420
|
/**
|
|
424
421
|
* Forces reload of pictures/sequences layer styles.
|
|
425
422
|
* This is useful after a map theme change.
|
|
423
|
+
* @memberof Panoramax.components.ui.Map#
|
|
426
424
|
*/
|
|
427
425
|
reloadLayersStyles() {
|
|
428
426
|
const updateStyle = (layer, style) => {
|
|
@@ -438,30 +436,12 @@ export default class Map extends maplibregl.Map {
|
|
|
438
436
|
["pictures", "pictures_symbols", "sequences"].forEach(l => {
|
|
439
437
|
updateStyle(l, this._getLayerStyleProperties(l));
|
|
440
438
|
});
|
|
441
|
-
|
|
442
|
-
// Also handle the grid stats
|
|
443
|
-
if(this._hasGridStats() && this._parent?._mapFilters) {
|
|
444
|
-
let newType = "coef";
|
|
445
|
-
if(this._parent._mapFilters?.type) {
|
|
446
|
-
newType = this._parent._mapFilters.type == "flat" ? "coef_flat_pictures" : "coef_360_pictures";
|
|
447
|
-
}
|
|
448
|
-
this.getStyle().layers
|
|
449
|
-
.filter(l => l.id.endsWith("_grid"))
|
|
450
|
-
.forEach(l => {
|
|
451
|
-
const newl = switchCoefValue(l, newType);
|
|
452
|
-
for(let p in newl.layout) {
|
|
453
|
-
this.setLayoutProperty(l.id, p, newl.layout[p]);
|
|
454
|
-
}
|
|
455
|
-
for(let p in newl.paint) {
|
|
456
|
-
this.setPaintProperty(l.id, p, newl.paint[p]);
|
|
457
|
-
}
|
|
458
|
-
});
|
|
459
|
-
}
|
|
460
439
|
}
|
|
461
440
|
|
|
462
441
|
/**
|
|
463
442
|
* Creates source and layers for pictures and sequences.
|
|
464
443
|
* @private
|
|
444
|
+
* @memberof Panoramax.components.ui.Map#
|
|
465
445
|
* @param {string} id The source and layer ID prefix
|
|
466
446
|
*/
|
|
467
447
|
async _createPicturesTilesLayer(id) {
|
|
@@ -470,7 +450,7 @@ export default class Map extends maplibregl.Map {
|
|
|
470
450
|
|
|
471
451
|
// Load style from API
|
|
472
452
|
if(id !== "geovisio" && !this.getSource(`geovisio_${id}`)) {
|
|
473
|
-
const style = await this._parent.
|
|
453
|
+
const style = await this._parent.api.getUserMapStyle(id);
|
|
474
454
|
Object.entries(style.sources).forEach(([sId, s]) => this.addSource(sId, s));
|
|
475
455
|
style.layers = style.layers || [];
|
|
476
456
|
const layers = style.layers.concat(getMissingLayerStyles(style.sources, style.layers));
|
|
@@ -511,6 +491,7 @@ export default class Map extends maplibregl.Map {
|
|
|
511
491
|
// Sequences
|
|
512
492
|
const seqPlusLayerId = getUserLayerId(id, "sequences_plus");
|
|
513
493
|
this.on("mousemove", seqPlusLayerId, e => {
|
|
494
|
+
this._onSequenceHover(e);
|
|
514
495
|
if(this.getZoom() <= TILES_PICTURES_ZOOM+1) {
|
|
515
496
|
this.getCanvas().style.cursor = "pointer";
|
|
516
497
|
if(e.features[0].properties.id) {
|
|
@@ -580,6 +561,7 @@ export default class Map extends maplibregl.Map {
|
|
|
580
561
|
*
|
|
581
562
|
* @returns {object} Paint/layout properties
|
|
582
563
|
* @private
|
|
564
|
+
* @memberof Panoramax.components.ui.Map#
|
|
583
565
|
*/
|
|
584
566
|
_getLayerStyleProperties(layer) {
|
|
585
567
|
if(layer === "pictures_symbols") {
|
|
@@ -587,9 +569,9 @@ export default class Map extends maplibregl.Map {
|
|
|
587
569
|
"paint": {},
|
|
588
570
|
"layout": {
|
|
589
571
|
"icon-image": ["case",
|
|
590
|
-
["==", ["get", "id"], this._parent.
|
|
591
|
-
["==", ["get", "type"], "equirectangular"], "
|
|
592
|
-
"
|
|
572
|
+
["==", ["get", "id"], this._parent.picture], "",
|
|
573
|
+
["==", ["get", "type"], "equirectangular"], "pnx-arrow-360",
|
|
574
|
+
"pnx-arrow-flat"
|
|
593
575
|
],
|
|
594
576
|
"symbol-sort-key": this._getLayerSortStyle(layer),
|
|
595
577
|
},
|
|
@@ -614,6 +596,7 @@ export default class Map extends maplibregl.Map {
|
|
|
614
596
|
/**
|
|
615
597
|
* Retrieve map layer color scheme according to selected theme.
|
|
616
598
|
* @private
|
|
599
|
+
* @memberof Panoramax.components.ui.Map#
|
|
617
600
|
*/
|
|
618
601
|
_getLayerColorStyle(layer) {
|
|
619
602
|
// Hidden style
|
|
@@ -623,7 +606,7 @@ export default class Map extends maplibregl.Map {
|
|
|
623
606
|
];
|
|
624
607
|
|
|
625
608
|
// Selected sequence style
|
|
626
|
-
const seqId = this._parent.
|
|
609
|
+
const seqId = this._parent.sequence;
|
|
627
610
|
if(layer == "sequences" && seqId) {
|
|
628
611
|
s.push(["==", ["get", "id"], seqId], COLORS.SELECTED);
|
|
629
612
|
}
|
|
@@ -640,6 +623,7 @@ export default class Map extends maplibregl.Map {
|
|
|
640
623
|
/**
|
|
641
624
|
* Retrieve map sort key according to selected theme.
|
|
642
625
|
* @private
|
|
626
|
+
* @memberof Panoramax.components.ui.Map#
|
|
643
627
|
*/
|
|
644
628
|
_getLayerSortStyle(layer) {
|
|
645
629
|
// Values
|
|
@@ -654,7 +638,7 @@ export default class Map extends maplibregl.Map {
|
|
|
654
638
|
];
|
|
655
639
|
|
|
656
640
|
// Selected sequence style
|
|
657
|
-
const seqId = this._parent.
|
|
641
|
+
const seqId = this._parent.sequence;
|
|
658
642
|
if(layer == "sequences" && seqId) {
|
|
659
643
|
s.push(["==", ["get", "id"], seqId], 100);
|
|
660
644
|
}
|
|
@@ -671,6 +655,7 @@ export default class Map extends maplibregl.Map {
|
|
|
671
655
|
* @private
|
|
672
656
|
* @param {object} e The event thrown by MapLibre
|
|
673
657
|
* @param {string} from The event source layer
|
|
658
|
+
* @memberof Panoramax.components.ui.Map#
|
|
674
659
|
*/
|
|
675
660
|
_attachPreviewToPictures(e, from) {
|
|
676
661
|
let f = e.features.pop();
|
|
@@ -720,7 +705,7 @@ export default class Map extends maplibregl.Map {
|
|
|
720
705
|
|
|
721
706
|
if(thumbUrl) {
|
|
722
707
|
let content = document.createElement("img");
|
|
723
|
-
content.classList.add("
|
|
708
|
+
content.classList.add("pnx-map-thumb");
|
|
724
709
|
content.alt = this._parent._t.map.thumbnail;
|
|
725
710
|
let img = new Image();
|
|
726
711
|
img.src = thumbUrl;
|
|
@@ -737,7 +722,7 @@ export default class Map extends maplibregl.Map {
|
|
|
737
722
|
|
|
738
723
|
if(f.properties.hidden) {
|
|
739
724
|
const legend = document.createElement("div");
|
|
740
|
-
legend.classList.add("
|
|
725
|
+
legend.classList.add("pnx-map-thumb-legend");
|
|
741
726
|
legend.appendChild(document.createTextNode(this._parent._t.map.not_public));
|
|
742
727
|
const container = document.createElement("div");
|
|
743
728
|
container.appendChild(content);
|
|
@@ -772,11 +757,12 @@ export default class Map extends maplibregl.Map {
|
|
|
772
757
|
* @param {LngLat} coordinates The map coordinates
|
|
773
758
|
* @returns {Promise} Promise resolving on picture thumbnail URL, or null on timeout
|
|
774
759
|
* @private
|
|
760
|
+
* @memberof Panoramax.components.ui.Map#
|
|
775
761
|
*/
|
|
776
762
|
_getThumbURL(coordinates) {
|
|
777
|
-
return this._parent.
|
|
763
|
+
return this._parent.api.getPicturesAroundCoordinates(coordinates[1], coordinates[0], 0.1, 1).then(res => {
|
|
778
764
|
const p = res?.features?.pop();
|
|
779
|
-
return p ? this._parent.
|
|
765
|
+
return p ? this._parent.api.findThumbnailInPictureFeature(p) : null;
|
|
780
766
|
});
|
|
781
767
|
}
|
|
782
768
|
|
|
@@ -788,21 +774,22 @@ export default class Map extends maplibregl.Map {
|
|
|
788
774
|
* @param {LngLat} [coordinates] The map coordinates
|
|
789
775
|
* @returns {Promise} Promise resolving on picture thumbnail URL, or null on timeout
|
|
790
776
|
* @private
|
|
777
|
+
* @memberof Panoramax.components.ui.Map#
|
|
791
778
|
*/
|
|
792
779
|
_getSequenceThumbURL(seqId, coordinates) {
|
|
793
780
|
if(coordinates) {
|
|
794
|
-
return this._parent.
|
|
781
|
+
return this._parent.api.getPicturesAroundCoordinates(coordinates.lat, coordinates.lng, 1, 1, seqId)
|
|
795
782
|
.then(results => {
|
|
796
783
|
if(results?.features?.length > 0) {
|
|
797
|
-
return this._parent.
|
|
784
|
+
return this._parent.api.findThumbnailInPictureFeature(results.features[0]);
|
|
798
785
|
}
|
|
799
786
|
else {
|
|
800
|
-
return this._parent.
|
|
787
|
+
return this._parent.api.getPictureThumbnailURLForSequence(seqId);
|
|
801
788
|
}
|
|
802
789
|
});
|
|
803
790
|
}
|
|
804
791
|
else {
|
|
805
|
-
return this._parent.
|
|
792
|
+
return this._parent.api.getPictureThumbnailURLForSequence(seqId);
|
|
806
793
|
}
|
|
807
794
|
}
|
|
808
795
|
|
|
@@ -813,7 +800,7 @@ export default class Map extends maplibregl.Map {
|
|
|
813
800
|
* @param {string} picId The picture ID
|
|
814
801
|
* @param {string} [seqId] The sequence ID (can speed up search if available)
|
|
815
802
|
* @returns {Promise} Promise resolving on picture thumbnail URL, or null on timeout
|
|
816
|
-
*
|
|
803
|
+
* @memberof Panoramax.components.ui.Map#
|
|
817
804
|
* @private
|
|
818
805
|
*/
|
|
819
806
|
_getPictureThumbURL(picId, seqId) {
|
|
@@ -824,7 +811,7 @@ export default class Map extends maplibregl.Map {
|
|
|
824
811
|
res = typeof this._picThumbUrl[picId] === "string" ? Promise.resolve(this._picThumbUrl[picId]) : this._picThumbUrl[picId];
|
|
825
812
|
}
|
|
826
813
|
else {
|
|
827
|
-
this._picThumbUrl[picId] = this._parent.
|
|
814
|
+
this._picThumbUrl[picId] = this._parent.api.getPictureThumbnailURL(picId, seqId).then(url => {
|
|
828
815
|
if(url) {
|
|
829
816
|
this._picThumbUrl[picId] = url;
|
|
830
817
|
return url;
|
|
@@ -849,6 +836,7 @@ export default class Map extends maplibregl.Map {
|
|
|
849
836
|
*
|
|
850
837
|
* @returns {maplibregl.Marker} The generated marker
|
|
851
838
|
* @private
|
|
839
|
+
* @memberof Panoramax.components.ui.Map#
|
|
852
840
|
*/
|
|
853
841
|
_getPictureMarker(selected = true) {
|
|
854
842
|
const img = document.createElement("img");
|
|
@@ -863,6 +851,7 @@ export default class Map extends maplibregl.Map {
|
|
|
863
851
|
* Event handler for sequence hover
|
|
864
852
|
* @private
|
|
865
853
|
* @param {object} e Event data
|
|
854
|
+
* @memberof Panoramax.components.ui.Map#
|
|
866
855
|
*/
|
|
867
856
|
_onSequenceHover(e) {
|
|
868
857
|
e.preventDefault();
|
|
@@ -870,17 +859,11 @@ export default class Map extends maplibregl.Map {
|
|
|
870
859
|
/**
|
|
871
860
|
* Event when a sequence on map is hovered (not selected)
|
|
872
861
|
*
|
|
873
|
-
* @event
|
|
874
|
-
* @
|
|
875
|
-
* @
|
|
876
|
-
* @property {object} detail Event information
|
|
877
|
-
* @property {string} detail.seqId The hovered sequence ID
|
|
862
|
+
* @event Panoramax.components.ui.Map#sequence-hover
|
|
863
|
+
* @type {maplibregl.util.evented.Event}
|
|
864
|
+
* @property {string} seqId The hovered sequence ID
|
|
878
865
|
*/
|
|
879
|
-
this.
|
|
880
|
-
detail: {
|
|
881
|
-
seqId: e.features[0].properties.id
|
|
882
|
-
}
|
|
883
|
-
}));
|
|
866
|
+
this.fire("sequence-hover", { seqId: e.features[0].properties.id });
|
|
884
867
|
}
|
|
885
868
|
}
|
|
886
869
|
|
|
@@ -888,26 +871,22 @@ export default class Map extends maplibregl.Map {
|
|
|
888
871
|
* Event handler for sequence click
|
|
889
872
|
* @private
|
|
890
873
|
* @param {object} e Event data
|
|
874
|
+
* @memberof Panoramax.components.ui.Map#
|
|
891
875
|
*/
|
|
892
876
|
_onSequenceClick(e) {
|
|
893
877
|
e.preventDefault();
|
|
894
878
|
if(e.features.length > 0 && e.features[0].properties?.id) {
|
|
895
879
|
/**
|
|
896
880
|
* Event when a sequence on map is clicked
|
|
897
|
-
*
|
|
898
|
-
* @
|
|
899
|
-
* @
|
|
900
|
-
* @
|
|
901
|
-
* @property {object} detail Event information
|
|
902
|
-
* @property {string} detail.seqId The clicked sequence ID
|
|
903
|
-
* @property {maplibregl.LngLat} detail.coordinates The coordinates of user click
|
|
881
|
+
* @event Panoramax.components.ui.Map#sequence-click
|
|
882
|
+
* @type {maplibregl.util.evented.Event}
|
|
883
|
+
* @property {string} seqId The clicked sequence ID
|
|
884
|
+
* @property {maplibregl.LngLat} coordinates The coordinates of user click
|
|
904
885
|
*/
|
|
905
|
-
this.
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
}
|
|
910
|
-
}));
|
|
886
|
+
this.fire("sequence-click", {
|
|
887
|
+
seqId: e.features[0].properties.id,
|
|
888
|
+
coordinates: e.lngLat
|
|
889
|
+
});
|
|
911
890
|
}
|
|
912
891
|
}
|
|
913
892
|
|
|
@@ -915,6 +894,7 @@ export default class Map extends maplibregl.Map {
|
|
|
915
894
|
* Event handler for picture click
|
|
916
895
|
* @private
|
|
917
896
|
* @param {object} e Event data
|
|
897
|
+
* @memberof Panoramax.components.ui.Map#
|
|
918
898
|
*/
|
|
919
899
|
_onPictureClick(e) {
|
|
920
900
|
e.preventDefault();
|
|
@@ -935,21 +915,17 @@ export default class Map extends maplibregl.Map {
|
|
|
935
915
|
/**
|
|
936
916
|
* Event when a picture on map is clicked
|
|
937
917
|
*
|
|
938
|
-
* @event
|
|
939
|
-
* @
|
|
940
|
-
* @
|
|
941
|
-
* @property {
|
|
942
|
-
* @property {
|
|
943
|
-
* @property {string} detail.seqId The clicked picture's sequence ID
|
|
944
|
-
* @property {object} detail.feature The GeoJSON feature of the picture
|
|
918
|
+
* @event Panoramax.components.ui.Map#picture-click
|
|
919
|
+
* @type {maplibregl.util.evented.Event}
|
|
920
|
+
* @property {string} picId The clicked picture ID
|
|
921
|
+
* @property {string} seqId The clicked picture's sequence ID
|
|
922
|
+
* @property {object} feature The GeoJSON feature of the picture
|
|
945
923
|
*/
|
|
946
|
-
this.
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
}
|
|
952
|
-
}));
|
|
924
|
+
this.fire("picture-click", {
|
|
925
|
+
picId: f.properties.id,
|
|
926
|
+
seqId,
|
|
927
|
+
feature: f
|
|
928
|
+
});
|
|
953
929
|
}
|
|
954
930
|
}
|
|
955
931
|
}
|