umap-project 3.3.2__py3-none-any.whl → 3.4.0__py3-none-any.whl
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.
- umap/__init__.py +1 -1
- umap/context_processors.py +4 -1
- umap/locale/cs_CZ/LC_MESSAGES/django.mo +0 -0
- umap/locale/cs_CZ/LC_MESSAGES/django.po +43 -33
- umap/locale/da/LC_MESSAGES/django.mo +0 -0
- umap/locale/da/LC_MESSAGES/django.po +43 -33
- umap/locale/de/LC_MESSAGES/django.mo +0 -0
- umap/locale/de/LC_MESSAGES/django.po +64 -53
- umap/locale/el/LC_MESSAGES/django.mo +0 -0
- umap/locale/el/LC_MESSAGES/django.po +35 -29
- umap/locale/en/LC_MESSAGES/django.po +47 -41
- umap/locale/es/LC_MESSAGES/django.mo +0 -0
- umap/locale/es/LC_MESSAGES/django.po +43 -33
- umap/locale/et/LC_MESSAGES/django.mo +0 -0
- umap/locale/et/LC_MESSAGES/django.po +58 -54
- umap/locale/eu/LC_MESSAGES/django.mo +0 -0
- umap/locale/eu/LC_MESSAGES/django.po +43 -33
- umap/locale/fa_IR/LC_MESSAGES/django.mo +0 -0
- umap/locale/fa_IR/LC_MESSAGES/django.po +43 -33
- umap/locale/fr/LC_MESSAGES/django.mo +0 -0
- umap/locale/fr/LC_MESSAGES/django.po +36 -30
- umap/locale/gl/LC_MESSAGES/django.mo +0 -0
- umap/locale/gl/LC_MESSAGES/django.po +43 -33
- umap/locale/hu/LC_MESSAGES/django.mo +0 -0
- umap/locale/hu/LC_MESSAGES/django.po +35 -29
- umap/locale/is/LC_MESSAGES/django.mo +0 -0
- umap/locale/is/LC_MESSAGES/django.po +43 -33
- umap/locale/it/LC_MESSAGES/django.mo +0 -0
- umap/locale/it/LC_MESSAGES/django.po +43 -33
- umap/locale/nl/LC_MESSAGES/django.mo +0 -0
- umap/locale/nl/LC_MESSAGES/django.po +35 -29
- umap/locale/pl/LC_MESSAGES/django.mo +0 -0
- umap/locale/pl/LC_MESSAGES/django.po +114 -103
- umap/locale/pt/LC_MESSAGES/django.mo +0 -0
- umap/locale/pt/LC_MESSAGES/django.po +43 -33
- umap/locale/th_TH/LC_MESSAGES/django.mo +0 -0
- umap/locale/th_TH/LC_MESSAGES/django.po +310 -109
- umap/locale/zh_TW/LC_MESSAGES/django.mo +0 -0
- umap/locale/zh_TW/LC_MESSAGES/django.po +80 -70
- umap/management/commands/switch_user.py +2 -2
- umap/migrations/0018_datalayer_uuid.py +1 -1
- umap/models.py +7 -3
- umap/settings/local.py.sample +1 -1
- umap/static/umap/base.css +89 -32
- umap/static/umap/content.css +129 -33
- umap/static/umap/css/bar.css +82 -20
- umap/static/umap/css/browser.css +163 -0
- umap/static/umap/css/contextmenu.css +15 -0
- umap/static/umap/css/dialog.css +36 -16
- umap/static/umap/css/form.css +123 -33
- umap/static/umap/css/icon.css +46 -3
- umap/static/umap/css/panel.css +7 -3
- umap/static/umap/css/popup.css +34 -8
- umap/static/umap/css/tooltip.css +8 -4
- umap/static/umap/img/16-white.svg +26 -8
- umap/static/umap/img/16.svg +1 -1
- umap/static/umap/img/source/16-white.svg +36 -18
- umap/static/umap/img/source/16.svg +1 -1
- umap/static/umap/js/components/alerts/alert.css +69 -31
- umap/static/umap/js/components/alerts/alert.js +20 -2
- umap/static/umap/js/components/base.js +1 -1
- umap/static/umap/js/modules/browser.js +69 -61
- umap/static/umap/js/modules/caption.js +10 -7
- umap/static/umap/js/modules/data/features.js +89 -63
- umap/static/umap/js/modules/data/fields.js +446 -0
- umap/static/umap/js/modules/data/layer.js +116 -196
- umap/static/umap/js/modules/domutils.js +109 -0
- umap/static/umap/js/modules/filters.js +780 -0
- umap/static/umap/js/modules/form/builder.js +8 -5
- umap/static/umap/js/modules/form/fields.js +111 -221
- umap/static/umap/js/modules/formatter.js +24 -1
- umap/static/umap/js/modules/help.js +4 -3
- umap/static/umap/js/modules/i18n.js +1 -1
- umap/static/umap/js/modules/importer.js +1 -1
- umap/static/umap/js/modules/importers/opendata.js +15 -0
- umap/static/umap/js/modules/importers/openrouteservice.js +6 -1
- umap/static/umap/js/modules/managers.js +2 -1
- umap/static/umap/js/modules/permissions.js +39 -31
- umap/static/umap/js/modules/rendering/controls.js +11 -9
- umap/static/umap/js/modules/rendering/icon.js +3 -8
- umap/static/umap/js/modules/rendering/layers/base.js +3 -3
- umap/static/umap/js/modules/rendering/layers/classified.js +18 -11
- umap/static/umap/js/modules/rendering/layers/cluster.js +23 -11
- umap/static/umap/js/modules/rendering/layers/heat.js +27 -21
- umap/static/umap/js/modules/rendering/map.js +1 -0
- umap/static/umap/js/modules/rendering/template.js +50 -23
- umap/static/umap/js/modules/rendering/ui.js +33 -25
- umap/static/umap/js/modules/rules.js +38 -44
- umap/static/umap/js/modules/schema.js +3 -6
- umap/static/umap/js/modules/share.js +5 -4
- umap/static/umap/js/modules/tableeditor.js +50 -38
- umap/static/umap/js/modules/templates.js +2 -3
- umap/static/umap/js/modules/ui/bar.js +55 -23
- umap/static/umap/js/modules/ui/dialog.js +38 -27
- umap/static/umap/js/modules/ui/panel.js +23 -8
- umap/static/umap/js/modules/ui/tooltip.js +6 -5
- umap/static/umap/js/modules/umap.js +158 -51
- umap/static/umap/js/modules/utils.js +24 -2
- umap/static/umap/js/umap.core.js +1 -110
- umap/static/umap/locale/am_ET.js +52 -17
- umap/static/umap/locale/am_ET.json +52 -17
- umap/static/umap/locale/ar.js +52 -17
- umap/static/umap/locale/ar.json +52 -17
- umap/static/umap/locale/ast.js +52 -17
- umap/static/umap/locale/ast.json +52 -17
- umap/static/umap/locale/bg.js +52 -17
- umap/static/umap/locale/bg.json +52 -17
- umap/static/umap/locale/br.js +48 -22
- umap/static/umap/locale/br.json +48 -22
- umap/static/umap/locale/ca.js +52 -17
- umap/static/umap/locale/ca.json +52 -17
- umap/static/umap/locale/cs_CZ.js +52 -17
- umap/static/umap/locale/cs_CZ.json +52 -17
- umap/static/umap/locale/da.js +54 -17
- umap/static/umap/locale/da.json +54 -17
- umap/static/umap/locale/de.js +102 -67
- umap/static/umap/locale/de.json +102 -67
- umap/static/umap/locale/el.js +52 -17
- umap/static/umap/locale/el.json +52 -17
- umap/static/umap/locale/en.js +54 -16
- umap/static/umap/locale/en.json +54 -16
- umap/static/umap/locale/en_US.json +52 -17
- umap/static/umap/locale/es.js +54 -17
- umap/static/umap/locale/es.json +54 -17
- umap/static/umap/locale/et.js +91 -56
- umap/static/umap/locale/et.json +91 -56
- umap/static/umap/locale/eu.js +84 -49
- umap/static/umap/locale/eu.json +84 -49
- umap/static/umap/locale/fa_IR.js +52 -17
- umap/static/umap/locale/fa_IR.json +52 -17
- umap/static/umap/locale/fi.js +52 -17
- umap/static/umap/locale/fi.json +52 -17
- umap/static/umap/locale/fr.js +54 -17
- umap/static/umap/locale/fr.json +54 -17
- umap/static/umap/locale/gl.js +52 -17
- umap/static/umap/locale/gl.json +52 -17
- umap/static/umap/locale/he.js +52 -17
- umap/static/umap/locale/he.json +52 -17
- umap/static/umap/locale/hr.js +52 -17
- umap/static/umap/locale/hr.json +52 -17
- umap/static/umap/locale/hu.js +59 -24
- umap/static/umap/locale/hu.json +59 -24
- umap/static/umap/locale/id.js +52 -17
- umap/static/umap/locale/id.json +52 -17
- umap/static/umap/locale/is.js +52 -17
- umap/static/umap/locale/is.json +52 -17
- umap/static/umap/locale/it.js +52 -17
- umap/static/umap/locale/it.json +52 -17
- umap/static/umap/locale/ja.js +52 -17
- umap/static/umap/locale/ja.json +52 -17
- umap/static/umap/locale/ko.js +52 -17
- umap/static/umap/locale/ko.json +52 -17
- umap/static/umap/locale/lt.js +52 -17
- umap/static/umap/locale/lt.json +52 -17
- umap/static/umap/locale/ms.js +52 -17
- umap/static/umap/locale/ms.json +52 -17
- umap/static/umap/locale/nl.js +52 -17
- umap/static/umap/locale/nl.json +52 -17
- umap/static/umap/locale/no.js +52 -17
- umap/static/umap/locale/no.json +52 -17
- umap/static/umap/locale/pl.js +53 -17
- umap/static/umap/locale/pl.json +53 -17
- umap/static/umap/locale/pl_PL.json +52 -17
- umap/static/umap/locale/pt.js +52 -17
- umap/static/umap/locale/pt.json +52 -17
- umap/static/umap/locale/pt_BR.js +52 -17
- umap/static/umap/locale/pt_BR.json +52 -17
- umap/static/umap/locale/pt_PT.js +52 -17
- umap/static/umap/locale/pt_PT.json +52 -17
- umap/static/umap/locale/ro.js +52 -17
- umap/static/umap/locale/ro.json +52 -17
- umap/static/umap/locale/ru.js +52 -17
- umap/static/umap/locale/ru.json +52 -17
- umap/static/umap/locale/si.js +1 -1
- umap/static/umap/locale/si.json +1 -1
- umap/static/umap/locale/sk_SK.js +52 -17
- umap/static/umap/locale/sk_SK.json +52 -17
- umap/static/umap/locale/sl.js +52 -17
- umap/static/umap/locale/sl.json +52 -17
- umap/static/umap/locale/sr.js +52 -17
- umap/static/umap/locale/sr.json +52 -17
- umap/static/umap/locale/sv.js +52 -17
- umap/static/umap/locale/sv.json +52 -17
- umap/static/umap/locale/th_TH.js +52 -17
- umap/static/umap/locale/th_TH.json +52 -17
- umap/static/umap/locale/tr.js +52 -17
- umap/static/umap/locale/tr.json +52 -17
- umap/static/umap/locale/uk_UA.js +52 -17
- umap/static/umap/locale/uk_UA.json +52 -17
- umap/static/umap/locale/vi.js +52 -17
- umap/static/umap/locale/vi.json +52 -17
- umap/static/umap/locale/vi_VN.json +52 -17
- umap/static/umap/locale/zh.js +52 -17
- umap/static/umap/locale/zh.json +52 -17
- umap/static/umap/locale/zh_CN.json +52 -17
- umap/static/umap/locale/zh_TW.Big5.json +52 -17
- umap/static/umap/locale/zh_TW.js +53 -17
- umap/static/umap/locale/zh_TW.json +53 -17
- umap/static/umap/map.css +63 -226
- umap/static/umap/unittests/utils.js +18 -0
- umap/static/umap/vars.css +23 -5
- umap/templates/umap/components/alerts/alert.html +32 -29
- umap/templates/umap/css.html +2 -1
- umap/templates/umap/login_popup_end.html +18 -9
- umap/templates/umap/user_map_table.html +7 -2
- umap/tests/integration/conftest.py +10 -6
- umap/tests/integration/test_anonymous_owned_map.py +90 -37
- umap/tests/integration/test_basics.py +25 -1
- umap/tests/integration/test_browser.py +37 -0
- umap/tests/integration/test_cluster.py +110 -0
- umap/tests/integration/test_conditional_rules.py +107 -52
- umap/tests/integration/test_datalayer.py +9 -16
- umap/tests/integration/test_draw_polygon.py +6 -0
- umap/tests/integration/test_draw_polyline.py +11 -0
- umap/tests/integration/test_edit_marker.py +12 -1
- umap/tests/integration/test_export_map.py +19 -0
- umap/tests/integration/test_fields.py +541 -0
- umap/tests/integration/test_filters.py +616 -0
- umap/tests/integration/test_iframe.py +1 -1
- umap/tests/integration/test_import.py +38 -42
- umap/tests/integration/test_map_preview.py +1 -1
- umap/tests/integration/test_picto.py +1 -1
- umap/tests/integration/test_popup.py +31 -0
- umap/tests/integration/test_remote_data.py +60 -4
- umap/tests/integration/test_save.py +1 -1
- umap/tests/integration/test_share.py +4 -4
- umap/tests/integration/test_tableeditor.py +31 -7
- umap/tests/integration/test_websocket_sync.py +71 -20
- umap/tests/test_dashboard.py +11 -1
- umap/tests/test_statics.py +2 -2
- umap/tests/test_utils.py +19 -2
- umap/tests/test_views.py +1 -1
- umap/urls.py +1 -0
- umap/utils.py +8 -1
- umap/views.py +5 -0
- {umap_project-3.3.2.dist-info → umap_project-3.4.0.dist-info}/METADATA +15 -15
- {umap_project-3.3.2.dist-info → umap_project-3.4.0.dist-info}/RECORD +240 -236
- umap/static/umap/js/modules/facets.js +0 -164
- umap/tests/integration/test_facets_browser.py +0 -279
- {umap_project-3.3.2.dist-info → umap_project-3.4.0.dist-info}/WHEEL +0 -0
- {umap_project-3.3.2.dist-info → umap_project-3.4.0.dist-info}/entry_points.txt +0 -0
- {umap_project-3.3.2.dist-info → umap_project-3.4.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -2,7 +2,6 @@ import { DomEvent, DomUtil, stamp } from '../../vendors/leaflet/leaflet-src.esm.
|
|
|
2
2
|
import { Form } from './form/builder.js'
|
|
3
3
|
import { EXPORT_FORMATS } from './formatter.js'
|
|
4
4
|
import { translate } from './i18n.js'
|
|
5
|
-
import * as Icon from './rendering/icon.js'
|
|
6
5
|
import ContextMenu from './ui/contextmenu.js'
|
|
7
6
|
import * as Utils from './utils.js'
|
|
8
7
|
import { SCHEMA } from './schema.js'
|
|
@@ -23,28 +22,22 @@ export default class Browser {
|
|
|
23
22
|
if (feature.isFiltered()) return
|
|
24
23
|
if (this.options.inBbox && !feature.isOnScreen(this.bounds)) return
|
|
25
24
|
const template = `
|
|
26
|
-
<li class="feature ${feature.getClassName()}">
|
|
27
|
-
<
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
<span
|
|
25
|
+
<li class="feature ${feature.getClassName()} ${feature.getUniqueClassName()} with-toolbox">
|
|
26
|
+
<span>
|
|
27
|
+
<i class="icon icon-16 icon-${feature.getClassName()} feature-color" data-ref=colorBox></i>
|
|
28
|
+
<span class="feature-title truncate" data-ref=label></span>
|
|
29
|
+
</span>
|
|
30
|
+
<span>
|
|
31
|
+
<button class="icon icon-16 icon-zoom" title="${translate('Bring feature to center')}" data-ref=zoom></button
|
|
32
|
+
><button class="icon icon-16 show-on-edit icon-edit" title="${translate('Edit this feature')}" data-ref=edit></button
|
|
33
|
+
><button class="icon icon-16 show-on-edit icon-delete" title="${translate('Delete this feature')}" data-ref=remove></button>
|
|
34
|
+
</span>
|
|
32
35
|
</li>
|
|
33
36
|
`
|
|
34
37
|
const [row, { zoom, edit, remove, colorBox, label }] =
|
|
35
38
|
Utils.loadTemplateWithRefs(template)
|
|
36
39
|
label.textContent = label.title = feature.getDisplayName() || '—'
|
|
37
|
-
|
|
38
|
-
? Icon.formatUrl(feature._getIconUrl(), feature)
|
|
39
|
-
: null
|
|
40
|
-
const bgcolor = feature.getPreviewColor()
|
|
41
|
-
colorBox.style.backgroundColor = bgcolor
|
|
42
|
-
if (symbol && symbol !== SCHEMA.iconUrl.default) {
|
|
43
|
-
const icon = Icon.makeElement(symbol, colorBox)
|
|
44
|
-
Icon.setContrast(icon, colorBox, symbol, bgcolor)
|
|
45
|
-
} else if (DomUtil.contrastedColor(colorBox, bgcolor)) {
|
|
46
|
-
colorBox.classList.add('icon-white')
|
|
47
|
-
}
|
|
40
|
+
feature.makePreview(colorBox)
|
|
48
41
|
const viewFeature = (e) => {
|
|
49
42
|
feature.zoomTo({ ...e, callback: () => feature.view() })
|
|
50
43
|
}
|
|
@@ -65,21 +58,23 @@ export default class Browser {
|
|
|
65
58
|
addDataLayer(datalayer, parent) {
|
|
66
59
|
const open = this.mode !== 'layers' ? ' open' : ''
|
|
67
60
|
const [container, { headline, toolbox, label }] = Utils.loadTemplateWithRefs(`
|
|
68
|
-
<details class="datalayer ${datalayer.
|
|
69
|
-
<summary data-ref=headline>
|
|
61
|
+
<details class="datalayer ${datalayer.cssId}" id="${this.datalayerId(datalayer)}"${open}>
|
|
62
|
+
<summary data-ref=headline class="with-toolbox">
|
|
63
|
+
<span>
|
|
64
|
+
<span class="datalayer-name truncate" data-id="${datalayer.id}" data-ref=label></span>
|
|
65
|
+
<span class="datalayer-counter"></span>
|
|
66
|
+
</span>
|
|
70
67
|
<span data-ref=toolbox></span>
|
|
71
|
-
<span class="datalayer-name" data-id="${datalayer.id}" data-ref=label></span>
|
|
72
|
-
<span class="datalayer-counter"></span>
|
|
73
68
|
</summary>
|
|
74
69
|
<ul></ul>
|
|
75
70
|
</details>
|
|
76
71
|
`)
|
|
77
72
|
datalayer.renderToolbox(toolbox)
|
|
78
73
|
parent.appendChild(container)
|
|
79
|
-
this.
|
|
74
|
+
this.updateFeaturesList(datalayer)
|
|
80
75
|
}
|
|
81
76
|
|
|
82
|
-
|
|
77
|
+
updateFeaturesList(datalayer) {
|
|
83
78
|
// Compute once, but use it for each feature later.
|
|
84
79
|
this.bounds = this._leafletMap.getBounds()
|
|
85
80
|
const id = this.datalayerId(datalayer)
|
|
@@ -102,14 +97,14 @@ export default class Browser {
|
|
|
102
97
|
}
|
|
103
98
|
|
|
104
99
|
toggleBadge() {
|
|
105
|
-
Utils.toggleBadge(this.filtersTitle, this.
|
|
106
|
-
Utils.toggleBadge('.umap-control-browse', this.
|
|
100
|
+
Utils.toggleBadge(this.filtersTitle, this.hasActiveFilters())
|
|
101
|
+
Utils.toggleBadge('.umap-control-browse', this.hasActiveFilters())
|
|
107
102
|
}
|
|
108
103
|
|
|
109
104
|
onFormChange() {
|
|
110
105
|
this._umap.datalayers.browsable().map((datalayer) => {
|
|
111
106
|
datalayer.resetLayer(true)
|
|
112
|
-
this.
|
|
107
|
+
this.updateFeaturesList(datalayer)
|
|
113
108
|
if (this._umap.fullPanel?.isOpen()) datalayer.tableEdit()
|
|
114
109
|
})
|
|
115
110
|
this.toggleBadge()
|
|
@@ -123,25 +118,24 @@ export default class Browser {
|
|
|
123
118
|
return !!document.querySelector('.on .umap-browser')
|
|
124
119
|
}
|
|
125
120
|
|
|
126
|
-
|
|
127
|
-
return !!this.options.filter || this._umap.
|
|
121
|
+
hasActiveFilters() {
|
|
122
|
+
return !!this.options.filter || this._umap.hasActiveFilters()
|
|
128
123
|
}
|
|
129
124
|
|
|
130
125
|
onMoveEnd() {
|
|
131
126
|
if (!this.isOpen()) return
|
|
132
|
-
const isListDynamic = this.options.inBbox
|
|
133
127
|
this._umap.datalayers.browsable().map((datalayer) => {
|
|
134
|
-
if (!
|
|
135
|
-
this.
|
|
128
|
+
if (!this.options.inBbox && !datalayer.hasDynamicData()) return
|
|
129
|
+
this.updateFeaturesList(datalayer)
|
|
136
130
|
})
|
|
137
131
|
}
|
|
138
132
|
|
|
139
133
|
update() {
|
|
140
134
|
if (!this.isOpen()) return
|
|
141
135
|
this.dataContainer.innerHTML = ''
|
|
142
|
-
this._umap.datalayers.browsable()
|
|
136
|
+
for (const datalayer of this._umap.datalayers.browsable()) {
|
|
143
137
|
this.addDataLayer(datalayer, this.dataContainer)
|
|
144
|
-
}
|
|
138
|
+
}
|
|
145
139
|
}
|
|
146
140
|
|
|
147
141
|
open(mode) {
|
|
@@ -151,11 +145,14 @@ export default class Browser {
|
|
|
151
145
|
<div>
|
|
152
146
|
<h3><i class="icon icon-16 icon-layers"></i>${translate('Data browser')}</h3>
|
|
153
147
|
<details class="filters" data-ref="details">
|
|
154
|
-
<summary data-ref=filtersTitle
|
|
148
|
+
<summary data-ref=filtersTitle>
|
|
149
|
+
<i class="icon icon-16 icon-filters"></i>${translate('Filters')}
|
|
150
|
+
</summary>
|
|
151
|
+
<button type="button" class="show-on-edit flat" data-ref=manageFilters>${translate('Manage filters')}</button>
|
|
155
152
|
<fieldset>
|
|
156
|
-
<div data-ref=formContainer>
|
|
153
|
+
<div data-ref="formContainer" class="formbox">
|
|
157
154
|
</div>
|
|
158
|
-
<button class="flat" type="button" data-ref=reset><i class="icon icon-16 icon-restore" title=""></i
|
|
155
|
+
<button class="flat" type="button" data-ref=reset><i class="icon icon-16 icon-restore" title=""></i> ${translate('Reset all')}</button>
|
|
159
156
|
</fieldset>
|
|
160
157
|
</details>
|
|
161
158
|
<div class="main-toolbox">
|
|
@@ -177,6 +174,7 @@ export default class Browser {
|
|
|
177
174
|
dataContainer,
|
|
178
175
|
formContainer,
|
|
179
176
|
reset,
|
|
177
|
+
manageFilters,
|
|
180
178
|
},
|
|
181
179
|
] = Utils.loadTemplateWithRefs(template)
|
|
182
180
|
// HOTFIX. Remove when this is released:
|
|
@@ -187,43 +185,53 @@ export default class Browser {
|
|
|
187
185
|
fitBounds.addEventListener('click', () => this._umap.fitDataBounds())
|
|
188
186
|
download.addEventListener('click', () => this.downloadVisible(download))
|
|
189
187
|
download.hidden = this._umap.getProperty('embedControl') === false
|
|
188
|
+
reset.addEventListener('click', () => this.resetFilters())
|
|
189
|
+
manageFilters.addEventListener('click', () => {
|
|
190
|
+
this._umap.edit().then((panel) => panel.scrollTo('details#fields-management'))
|
|
191
|
+
this._umap.filters.edit()
|
|
192
|
+
})
|
|
190
193
|
|
|
191
194
|
this.filtersTitle = filtersTitle
|
|
192
195
|
this.dataContainer = dataContainer
|
|
193
196
|
this.formContainer = formContainer
|
|
194
197
|
this.toggleBadge()
|
|
198
|
+
this.buildFilters()
|
|
199
|
+
this._umap.panel.open({
|
|
200
|
+
content: container,
|
|
201
|
+
className: 'umap-browser',
|
|
202
|
+
})
|
|
203
|
+
|
|
204
|
+
this.update()
|
|
205
|
+
}
|
|
195
206
|
|
|
196
|
-
|
|
207
|
+
buildFilters() {
|
|
208
|
+
this.formContainer.innerHTML = ''
|
|
209
|
+
const fields = [
|
|
197
210
|
[
|
|
198
211
|
'options.filter',
|
|
199
212
|
{ handler: 'Input', placeholder: translate('Search map features…') },
|
|
200
213
|
],
|
|
201
214
|
['options.inBbox', { handler: 'Switch', label: translate('Current map view') }],
|
|
202
215
|
]
|
|
203
|
-
const
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
window.setTimeout(builder.syncAll.bind(builder))
|
|
209
|
-
})
|
|
210
|
-
if (this._umap.properties.facetKey) {
|
|
211
|
-
fields = this._umap.facets.build()
|
|
212
|
-
filtersBuilder = new Form(this._umap.facets, fields)
|
|
213
|
-
filtersBuilder.on('set', () => this.onFormChange())
|
|
214
|
-
filtersBuilder.form.addEventListener('reset', () => {
|
|
215
|
-
window.setTimeout(filtersBuilder.syncAll.bind(filtersBuilder))
|
|
216
|
+
const searchForm = new Form(this, fields, { className: 'formbox' })
|
|
217
|
+
const listenFormChanges = (form) => {
|
|
218
|
+
form.on('set', () => this.onFormChange())
|
|
219
|
+
form.form.addEventListener('reset', () => {
|
|
220
|
+
window.setTimeout(form.syncAll.bind(form))
|
|
216
221
|
})
|
|
217
|
-
this.formContainer.appendChild(filtersBuilder.build())
|
|
218
222
|
}
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
this._umap.
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
}
|
|
225
|
-
|
|
226
|
-
|
|
223
|
+
this.formContainer.appendChild(searchForm.build())
|
|
224
|
+
listenFormChanges(searchForm)
|
|
225
|
+
if (this._umap.filters.size) {
|
|
226
|
+
const filtersForm = this._umap.filters.buildForm(this.formContainer)
|
|
227
|
+
listenFormChanges(filtersForm)
|
|
228
|
+
}
|
|
229
|
+
for (const datalayer of this._umap.datalayers.active()) {
|
|
230
|
+
if (datalayer.filters.size) {
|
|
231
|
+
const filtersForm = datalayer.filters.buildForm(this.formContainer)
|
|
232
|
+
listenFormChanges(filtersForm)
|
|
233
|
+
}
|
|
234
|
+
}
|
|
227
235
|
}
|
|
228
236
|
|
|
229
237
|
resetFilters() {
|
|
@@ -252,7 +260,7 @@ export default class Browser {
|
|
|
252
260
|
if (datalayer.isVisible()) allHidden = false
|
|
253
261
|
})
|
|
254
262
|
this._umap.datalayers.browsable().map((datalayer) => {
|
|
255
|
-
datalayer.
|
|
263
|
+
datalayer.autoVisibility = false
|
|
256
264
|
if (allHidden) {
|
|
257
265
|
datalayer.show()
|
|
258
266
|
} else {
|
|
@@ -5,7 +5,7 @@ import * as Utils from './utils.js'
|
|
|
5
5
|
const TEMPLATE = `
|
|
6
6
|
<div class="umap-caption">
|
|
7
7
|
<div class="header">
|
|
8
|
-
<i class="icon icon-16 icon-
|
|
8
|
+
<i class="icon icon-16 icon-info icon-block"></i>
|
|
9
9
|
<hgroup>
|
|
10
10
|
<h3><span class="map-name" data-ref="name"></span></h3>
|
|
11
11
|
<p data-ref="author"></p>
|
|
@@ -39,7 +39,7 @@ export default class Caption extends Utils.WithTemplate {
|
|
|
39
39
|
this._leafletMap = leafletMap
|
|
40
40
|
this.loadTemplate(TEMPLATE)
|
|
41
41
|
this.elements.star.addEventListener('click', async () => {
|
|
42
|
-
if (this._umap.
|
|
42
|
+
if (this._umap.permissions.userIsAuth()) {
|
|
43
43
|
await this._umap.star()
|
|
44
44
|
this.refresh()
|
|
45
45
|
} else {
|
|
@@ -96,11 +96,14 @@ export default class Caption extends Utils.WithTemplate {
|
|
|
96
96
|
addDataLayer(datalayer, parent) {
|
|
97
97
|
if (!datalayer.properties.inCaption) return
|
|
98
98
|
const template = `
|
|
99
|
-
<
|
|
100
|
-
<
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
99
|
+
<div class="caption-item ${datalayer.cssId}">
|
|
100
|
+
<p>
|
|
101
|
+
<span class="datalayer-legend"></span>
|
|
102
|
+
<strong data-ref="toolbox"></strong>
|
|
103
|
+
</p>
|
|
104
|
+
<p class="text" data-ref="description"></p>
|
|
105
|
+
</div>
|
|
106
|
+
`
|
|
104
107
|
const [element, { toolbox, description }] = Utils.loadTemplateWithRefs(template)
|
|
105
108
|
if (datalayer.properties.description) {
|
|
106
109
|
description.innerHTML = Utils.toHTML(datalayer.properties.description)
|
|
@@ -22,6 +22,8 @@ import {
|
|
|
22
22
|
} from '../rendering/ui.js'
|
|
23
23
|
import { SCHEMA } from '../schema.js'
|
|
24
24
|
import * as Utils from '../utils.js'
|
|
25
|
+
import * as DOMUtils from '../domutils.js'
|
|
26
|
+
import * as Icon from '../rendering/icon.js'
|
|
25
27
|
|
|
26
28
|
class Feature {
|
|
27
29
|
constructor(umap, datalayer, geojson = {}, id = null) {
|
|
@@ -91,7 +93,7 @@ class Feature {
|
|
|
91
93
|
|
|
92
94
|
get fields() {
|
|
93
95
|
// Fields are user defined properties
|
|
94
|
-
return [...this.
|
|
96
|
+
return [...this._umap.fields.all(), ...this.datalayer.fields.all()]
|
|
95
97
|
}
|
|
96
98
|
|
|
97
99
|
setter(key, value) {
|
|
@@ -136,6 +138,10 @@ class Feature {
|
|
|
136
138
|
return this.staticOptions.className
|
|
137
139
|
}
|
|
138
140
|
|
|
141
|
+
getUniqueClassName() {
|
|
142
|
+
return `feature-${this.datalayer.id}-${this.id}`
|
|
143
|
+
}
|
|
144
|
+
|
|
139
145
|
getPreviewColor() {
|
|
140
146
|
return this.getDynamicOption(this.staticOptions.mainColor)
|
|
141
147
|
}
|
|
@@ -213,10 +219,22 @@ class Feature {
|
|
|
213
219
|
return field.startsWith('properties.')
|
|
214
220
|
})
|
|
215
221
|
if (impactData) {
|
|
222
|
+
Utils.eachElement(`.${this.getUniqueClassName()} .feature-title`, (el) => {
|
|
223
|
+
el.textContent = this.getDisplayName()
|
|
224
|
+
el.title = this.getDisplayName()
|
|
225
|
+
})
|
|
216
226
|
if (this._umap.currentFeature === this) {
|
|
217
227
|
this.view()
|
|
218
228
|
}
|
|
219
229
|
}
|
|
230
|
+
const impactPreview = fields.some((field) => {
|
|
231
|
+
return field.startsWith('properties._umap_options')
|
|
232
|
+
})
|
|
233
|
+
if (impactPreview) {
|
|
234
|
+
Utils.eachElement(`.${this.getUniqueClassName()} .feature-color`, (el) => {
|
|
235
|
+
this.makePreview(el)
|
|
236
|
+
})
|
|
237
|
+
}
|
|
220
238
|
this.redraw()
|
|
221
239
|
}
|
|
222
240
|
|
|
@@ -233,7 +251,7 @@ class Feature {
|
|
|
233
251
|
)
|
|
234
252
|
|
|
235
253
|
let builder = new MutatingForm(this, [
|
|
236
|
-
['datalayer', { handler: '
|
|
254
|
+
['datalayer', { handler: 'EditableDataLayerSwitcher' }],
|
|
237
255
|
])
|
|
238
256
|
// removeLayer step will close the edit panel, let's reopen it
|
|
239
257
|
builder.on('set', () => this.edit(event))
|
|
@@ -241,11 +259,22 @@ class Feature {
|
|
|
241
259
|
|
|
242
260
|
const properties = []
|
|
243
261
|
for (const field of this.fields) {
|
|
244
|
-
|
|
245
|
-
if (field.key === 'description' || field.
|
|
246
|
-
handler = 'Textarea'
|
|
262
|
+
const options = { handler: 'Input', label: field.key }
|
|
263
|
+
if (field.key === 'description' || field.TYPE === 'Text') {
|
|
264
|
+
options.handler = 'Textarea'
|
|
265
|
+
options.helpEntries = ['textFormatting']
|
|
266
|
+
} else if (field.TYPE === 'Number') {
|
|
267
|
+
options.handler = 'FloatInput'
|
|
268
|
+
} else if (field.TYPE === 'Date') {
|
|
269
|
+
options.handler = 'DateInput'
|
|
270
|
+
} else if (field.TYPE === 'Datetime') {
|
|
271
|
+
options.handler = 'DateTimeInput'
|
|
272
|
+
} else if (field.TYPE === 'Boolean') {
|
|
273
|
+
options.handler = 'Switch'
|
|
274
|
+
} else if (field.TYPE === 'Enum') {
|
|
275
|
+
options.helpText = translate('Comma separated list of values')
|
|
247
276
|
}
|
|
248
|
-
properties.push([`properties.${field.key}`,
|
|
277
|
+
properties.push([`properties.${field.key}`, options])
|
|
249
278
|
}
|
|
250
279
|
builder = new MutatingForm(this, properties, {
|
|
251
280
|
id: 'umap-feature-properties',
|
|
@@ -256,13 +285,13 @@ class Feature {
|
|
|
256
285
|
`<button type="button"><i class="icon icon-16 icon-add"></i>${translate('Add a new field')}</button>`
|
|
257
286
|
)
|
|
258
287
|
button.addEventListener('click', () => {
|
|
259
|
-
this.datalayer.
|
|
288
|
+
this.datalayer.fields.editField().then(() => this.edit({ force: true }))
|
|
260
289
|
})
|
|
261
290
|
form.appendChild(button)
|
|
262
291
|
this.appendEditFieldsets(container)
|
|
263
292
|
const [details, { fieldset }] = Utils.loadTemplateWithRefs(`
|
|
264
293
|
<details>
|
|
265
|
-
<summary>${translate('Advanced actions')}</summary>
|
|
294
|
+
<summary><h4>${translate('Advanced actions')}</h4></summary>
|
|
266
295
|
<fieldset class="button-bar by2" data-ref=fieldset></fieldset>
|
|
267
296
|
</details>
|
|
268
297
|
`)
|
|
@@ -297,7 +326,7 @@ class Feature {
|
|
|
297
326
|
container.appendChild(button)
|
|
298
327
|
}
|
|
299
328
|
|
|
300
|
-
addExtraEditFieldset() {}
|
|
329
|
+
addExtraEditFieldset(container) {}
|
|
301
330
|
|
|
302
331
|
appendEditFieldsets(container) {
|
|
303
332
|
const optionsFields = this.getShapeOptions()
|
|
@@ -497,16 +526,16 @@ class Feature {
|
|
|
497
526
|
return properties
|
|
498
527
|
}
|
|
499
528
|
|
|
500
|
-
|
|
501
|
-
const oldValue = this.properties[
|
|
502
|
-
delete this.properties[
|
|
503
|
-
this.sync.update(`properties.${
|
|
529
|
+
deleteField(name) {
|
|
530
|
+
const oldValue = this.properties[name]
|
|
531
|
+
delete this.properties[name]
|
|
532
|
+
this.sync.update(`properties.${name}`, undefined, oldValue)
|
|
504
533
|
}
|
|
505
534
|
|
|
506
|
-
|
|
535
|
+
renameField(from, to) {
|
|
507
536
|
const oldValue = this.properties[from]
|
|
508
537
|
this.properties[to] = this.properties[from]
|
|
509
|
-
this.
|
|
538
|
+
this.deleteField(from)
|
|
510
539
|
this.sync.update(`properties.${to}`, oldValue, undefined)
|
|
511
540
|
}
|
|
512
541
|
|
|
@@ -522,12 +551,13 @@ class Feature {
|
|
|
522
551
|
isFiltered() {
|
|
523
552
|
const filterKeys = this.datalayer.getFilterKeys()
|
|
524
553
|
const filter = this._umap.browser.options.filter
|
|
525
|
-
if (filter && !this.
|
|
526
|
-
if (
|
|
554
|
+
if (filter && !this.matchFullTextFilter(filter, filterKeys)) return true
|
|
555
|
+
if (this._umap.filters.matchFeature(this)) return true
|
|
556
|
+
if (this.datalayer.filters.matchFeature(this)) return true
|
|
527
557
|
return false
|
|
528
558
|
}
|
|
529
559
|
|
|
530
|
-
|
|
560
|
+
matchFullTextFilter(filter, keys) {
|
|
531
561
|
filter = filter.toLowerCase()
|
|
532
562
|
// When user hasn't touched settings, when a feature has no name
|
|
533
563
|
// it will use the datalayer's name, so let's make the filtering
|
|
@@ -545,28 +575,6 @@ class Feature {
|
|
|
545
575
|
return false
|
|
546
576
|
}
|
|
547
577
|
|
|
548
|
-
matchFacets() {
|
|
549
|
-
const selected = this._umap.facets.selected
|
|
550
|
-
for (const [name, { type, min, max, choices }] of Object.entries(selected)) {
|
|
551
|
-
let value = this.properties[name]
|
|
552
|
-
const parser = this._umap.facets.getParser(type)
|
|
553
|
-
value = parser(value)
|
|
554
|
-
switch (type) {
|
|
555
|
-
case 'date':
|
|
556
|
-
case 'datetime':
|
|
557
|
-
case 'number':
|
|
558
|
-
if (!Number.isNaN(min) && !Number.isNaN(value) && min > value) return false
|
|
559
|
-
if (!Number.isNaN(max) && !Number.isNaN(value) && max < value) return false
|
|
560
|
-
break
|
|
561
|
-
default:
|
|
562
|
-
value = value || translate('<empty value>')
|
|
563
|
-
if (choices?.length && !choices.includes(value)) return false
|
|
564
|
-
break
|
|
565
|
-
}
|
|
566
|
-
}
|
|
567
|
-
return true
|
|
568
|
-
}
|
|
569
|
-
|
|
570
578
|
isMulti() {
|
|
571
579
|
return false
|
|
572
580
|
}
|
|
@@ -592,6 +600,7 @@ class Feature {
|
|
|
592
600
|
if (U.lang) properties.lang = U.lang
|
|
593
601
|
properties.rank = this.getRank() + 1
|
|
594
602
|
properties.layer = this.datalayer.getName()
|
|
603
|
+
properties.id = this.id
|
|
595
604
|
if (this.ui._map && this.hasGeom()) {
|
|
596
605
|
const center = this.center
|
|
597
606
|
properties.lat = center.lat
|
|
@@ -610,7 +619,7 @@ class Feature {
|
|
|
610
619
|
}
|
|
611
620
|
|
|
612
621
|
redraw() {
|
|
613
|
-
if (this.datalayer?.isVisible()) {
|
|
622
|
+
if (this.datalayer?.isVisible() && this.ui?.isVisible()) {
|
|
614
623
|
if (this.getUIClass() !== this.ui.getClass()) {
|
|
615
624
|
this.datalayer.hideFeature(this)
|
|
616
625
|
this.makeUI()
|
|
@@ -646,8 +655,7 @@ class Feature {
|
|
|
646
655
|
items.push({
|
|
647
656
|
label: translate('Copy as GeoJSON'),
|
|
648
657
|
action: () => {
|
|
649
|
-
|
|
650
|
-
this._umap.tooltip.open({ content: L._('✅ Copied!') })
|
|
658
|
+
DOMUtils.copyToClipboard(JSON.stringify(this.toGeoJSON()))
|
|
651
659
|
},
|
|
652
660
|
})
|
|
653
661
|
return items
|
|
@@ -706,6 +714,19 @@ class Feature {
|
|
|
706
714
|
this.ui.closePopup()
|
|
707
715
|
}
|
|
708
716
|
}
|
|
717
|
+
|
|
718
|
+
makePreview(element) {
|
|
719
|
+
element.innerHTML = ''
|
|
720
|
+
const symbol = this._getIconUrl ? Icon.formatUrl(this._getIconUrl(), this) : null
|
|
721
|
+
const bgcolor = this.getPreviewColor()
|
|
722
|
+
element.style.backgroundColor = bgcolor
|
|
723
|
+
if (symbol && symbol !== SCHEMA.iconUrl.default) {
|
|
724
|
+
const icon = Icon.makeElement(symbol, element)
|
|
725
|
+
Icon.setContrast(icon, element, symbol, bgcolor)
|
|
726
|
+
} else if (DOMUtils.contrastedColor(element, bgcolor)) {
|
|
727
|
+
element.classList.add('icon-white')
|
|
728
|
+
}
|
|
729
|
+
}
|
|
709
730
|
}
|
|
710
731
|
|
|
711
732
|
export class Point extends Feature {
|
|
@@ -931,6 +952,23 @@ class Path extends Feature {
|
|
|
931
952
|
}
|
|
932
953
|
return items
|
|
933
954
|
}
|
|
955
|
+
|
|
956
|
+
addExtraEditFieldset(container) {
|
|
957
|
+
const options = [
|
|
958
|
+
'properties._umap_options.textPath',
|
|
959
|
+
'properties._umap_options.textPathColor',
|
|
960
|
+
'properties._umap_options.textPathRepeat',
|
|
961
|
+
'properties._umap_options.textPathRotate',
|
|
962
|
+
'properties._umap_options.textPathSize',
|
|
963
|
+
'properties._umap_options.textPathOffset',
|
|
964
|
+
'properties._umap_options.textPathPosition',
|
|
965
|
+
]
|
|
966
|
+
const builder = new MutatingForm(this, options, {
|
|
967
|
+
id: 'umap-feature-line-decoration',
|
|
968
|
+
})
|
|
969
|
+
const fieldset = DomUtil.createFieldset(container, translate('Line decoration'))
|
|
970
|
+
fieldset.appendChild(builder.build())
|
|
971
|
+
}
|
|
934
972
|
}
|
|
935
973
|
|
|
936
974
|
export class LineString extends Path {
|
|
@@ -1229,26 +1267,6 @@ export class LineString extends Path {
|
|
|
1229
1267
|
button.addEventListener('click', async () => this.computeRoute())
|
|
1230
1268
|
}
|
|
1231
1269
|
|
|
1232
|
-
addExtraEditFieldset(container) {
|
|
1233
|
-
const options = [
|
|
1234
|
-
'properties._umap_options.textPath',
|
|
1235
|
-
'properties._umap_options.textPathColor',
|
|
1236
|
-
'properties._umap_options.textPathRepeat',
|
|
1237
|
-
'properties._umap_options.textPathRotate',
|
|
1238
|
-
'properties._umap_options.textPathSize',
|
|
1239
|
-
'properties._umap_options.textPathOffset',
|
|
1240
|
-
'properties._umap_options.textPathPosition',
|
|
1241
|
-
]
|
|
1242
|
-
const builder = new MutatingForm(this, options, {
|
|
1243
|
-
id: 'umap-feature-line-decoration',
|
|
1244
|
-
})
|
|
1245
|
-
const fieldset = DomUtil.createFieldset(container, translate('Line decoration'))
|
|
1246
|
-
fieldset.appendChild(builder.build())
|
|
1247
|
-
if (this._umap.properties.ORSAPIKey && this.isRoute()) {
|
|
1248
|
-
this._editRoute(container)
|
|
1249
|
-
}
|
|
1250
|
-
}
|
|
1251
|
-
|
|
1252
1270
|
async computeElevation() {
|
|
1253
1271
|
if (!this._umap.properties.ORSAPIKey) return
|
|
1254
1272
|
const importer = new OpenRouteService(this._umap)
|
|
@@ -1258,6 +1276,7 @@ export class LineString extends Path {
|
|
|
1258
1276
|
this.geometry = geometry
|
|
1259
1277
|
this.ui.resetTooltip()
|
|
1260
1278
|
this.sync.update('geometry', this.geometry, oldGeometry)
|
|
1279
|
+
Alert.success(translate('Elevation has been added!'))
|
|
1261
1280
|
}
|
|
1262
1281
|
}
|
|
1263
1282
|
|
|
@@ -1273,6 +1292,13 @@ export class LineString extends Path {
|
|
|
1273
1292
|
}
|
|
1274
1293
|
})
|
|
1275
1294
|
}
|
|
1295
|
+
|
|
1296
|
+
addExtraEditFieldset(container) {
|
|
1297
|
+
super.addExtraEditFieldset(container)
|
|
1298
|
+
if (this._umap.properties.ORSAPIKey && this.isRoute()) {
|
|
1299
|
+
this._editRoute(container)
|
|
1300
|
+
}
|
|
1301
|
+
}
|
|
1276
1302
|
}
|
|
1277
1303
|
|
|
1278
1304
|
export class Polygon extends Path {
|