mirror of
https://github.com/umap-project/umap.git
synced 2025-04-28 19:42:36 +02:00
chore: review with Alexis
This commit is contained in:
parent
51e41b7bce
commit
378e0f3ad3
26 changed files with 578 additions and 600 deletions
|
@ -63,15 +63,3 @@ When the data layers are initialized, they can have two states:
|
||||||
To mark what needs to be synced with the server, uMap currently mark objects as "dirty". Something marked as "dirty" has changed on the client, but is not yet saved on the server.
|
To mark what needs to be synced with the server, uMap currently mark objects as "dirty". Something marked as "dirty" has changed on the client, but is not yet saved on the server.
|
||||||
|
|
||||||
Each map, datalayer and permission objects can be marked as "dirty". When a change is made on an object, it will mark its parent as "dirty" as well, so it can be updated accordingly.
|
Each map, datalayer and permission objects can be marked as "dirty". When a change is made on an object, it will mark its parent as "dirty" as well, so it can be updated accordingly.
|
||||||
|
|
||||||
### Saving data to the server with `umap.save()`
|
|
||||||
|
|
||||||
Here is what's being done when you call `map.save()`:
|
|
||||||
|
|
||||||
1. `map.saveSelf()`, posting `name`, `center` and `settings` to the server, and then
|
|
||||||
2. calls `permission.save()`, which will post the permissions to the server, and then call back
|
|
||||||
3. `map.continueSaving()`, which will take the first dirtyLayer and call
|
|
||||||
4. `datalayer.save()` on it. It does the following:
|
|
||||||
1. Post the data (`name`, `displayOnLoad`, `rank`, `settings`, and `geojson`)
|
|
||||||
2. Calls `permission.save()`, posting `edit_status` to the server, and then calling `map.continue_saving()` and remove the datalayer from `dirtyDatalayers`.
|
|
||||||
5. When the `dirtyDatalayers` list is empty, we are done.
|
|
||||||
|
|
|
@ -6,9 +6,10 @@ import { EXPORT_FORMATS } from './formatter.js'
|
||||||
import ContextMenu from './ui/contextmenu.js'
|
import ContextMenu from './ui/contextmenu.js'
|
||||||
|
|
||||||
export default class Browser {
|
export default class Browser {
|
||||||
constructor(umap) {
|
constructor(umap, leafletMap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.umap._leafletMap.on('moveend', this.onMoveEnd, this)
|
this._leafletMap = leafletMap
|
||||||
|
this._leafletMap.on('moveend', this.onMoveEnd, this)
|
||||||
this.options = {
|
this.options = {
|
||||||
filter: '',
|
filter: '',
|
||||||
inBbox: false,
|
inBbox: false,
|
||||||
|
@ -82,7 +83,7 @@ export default class Browser {
|
||||||
|
|
||||||
updateDatalayer(datalayer) {
|
updateDatalayer(datalayer) {
|
||||||
// Compute once, but use it for each feature later.
|
// Compute once, but use it for each feature later.
|
||||||
this.bounds = this.umap._leafletMap.getBounds()
|
this.bounds = this._leafletMap.getBounds()
|
||||||
const parent = DomUtil.get(this.datalayerId(datalayer))
|
const parent = DomUtil.get(this.datalayerId(datalayer))
|
||||||
// Panel is not open
|
// Panel is not open
|
||||||
if (!parent) return
|
if (!parent) return
|
||||||
|
@ -115,10 +116,10 @@ export default class Browser {
|
||||||
}
|
}
|
||||||
|
|
||||||
onFormChange() {
|
onFormChange() {
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
datalayer.resetLayer(true)
|
datalayer.resetLayer(true)
|
||||||
this.updateDatalayer(datalayer)
|
this.updateDatalayer(datalayer)
|
||||||
if (this.umap.fullPanel?.isOpen()) datalayer.tableEdit()
|
if (this._umap.fullPanel?.isOpen()) datalayer.tableEdit()
|
||||||
})
|
})
|
||||||
this.toggleBadge()
|
this.toggleBadge()
|
||||||
}
|
}
|
||||||
|
@ -132,13 +133,13 @@ export default class Browser {
|
||||||
}
|
}
|
||||||
|
|
||||||
hasFilters() {
|
hasFilters() {
|
||||||
return !!this.options.filter || this.umap.facets.isActive()
|
return !!this.options.filter || this._umap.facets.isActive()
|
||||||
}
|
}
|
||||||
|
|
||||||
onMoveEnd() {
|
onMoveEnd() {
|
||||||
if (!this.isOpen()) return
|
if (!this.isOpen()) return
|
||||||
const isListDynamic = this.options.inBbox
|
const isListDynamic = this.options.inBbox
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
if (!isListDynamic && !datalayer.hasDynamicData()) return
|
if (!isListDynamic && !datalayer.hasDynamicData()) return
|
||||||
this.updateDatalayer(datalayer)
|
this.updateDatalayer(datalayer)
|
||||||
})
|
})
|
||||||
|
@ -147,7 +148,7 @@ export default class Browser {
|
||||||
update() {
|
update() {
|
||||||
if (!this.isOpen()) return
|
if (!this.isOpen()) return
|
||||||
this.dataContainer.innerHTML = ''
|
this.dataContainer.innerHTML = ''
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
this.addDataLayer(datalayer, this.dataContainer)
|
this.addDataLayer(datalayer, this.dataContainer)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -186,9 +187,9 @@ export default class Browser {
|
||||||
DomEvent.on(builder.form, 'reset', () => {
|
DomEvent.on(builder.form, 'reset', () => {
|
||||||
window.setTimeout(builder.syncAll.bind(builder))
|
window.setTimeout(builder.syncAll.bind(builder))
|
||||||
})
|
})
|
||||||
if (this.umap.properties.facetKey) {
|
if (this._umap.properties.facetKey) {
|
||||||
fields = this.umap.facets.build()
|
fields = this._umap.facets.build()
|
||||||
filtersBuilder = new L.FormBuilder(this.umap.facets, fields, {
|
filtersBuilder = new L.FormBuilder(this._umap.facets, fields, {
|
||||||
callback: () => this.onFormChange(),
|
callback: () => this.onFormChange(),
|
||||||
})
|
})
|
||||||
DomEvent.on(filtersBuilder.form, 'reset', () => {
|
DomEvent.on(filtersBuilder.form, 'reset', () => {
|
||||||
|
@ -206,7 +207,7 @@ export default class Browser {
|
||||||
textContent: translate('Reset all'),
|
textContent: translate('Reset all'),
|
||||||
})
|
})
|
||||||
|
|
||||||
this.umap.panel.open({
|
this._umap.panel.open({
|
||||||
content: container,
|
content: container,
|
||||||
className: 'umap-browser',
|
className: 'umap-browser',
|
||||||
})
|
})
|
||||||
|
@ -230,7 +231,7 @@ export default class Browser {
|
||||||
`)
|
`)
|
||||||
container.appendChild(toolbox)
|
container.appendChild(toolbox)
|
||||||
toggle.addEventListener('click', () => this.toggleLayers())
|
toggle.addEventListener('click', () => this.toggleLayers())
|
||||||
fitBounds.addEventListener('click', () => this.umap.fitDataBounds())
|
fitBounds.addEventListener('click', () => this._umap.fitDataBounds())
|
||||||
download.addEventListener('click', () => this.downloadVisible(download))
|
download.addEventListener('click', () => this.downloadVisible(download))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -240,7 +241,7 @@ export default class Browser {
|
||||||
for (const format of Object.keys(EXPORT_FORMATS)) {
|
for (const format of Object.keys(EXPORT_FORMATS)) {
|
||||||
items.push({
|
items.push({
|
||||||
label: format,
|
label: format,
|
||||||
action: () => this.umap.share.download(format),
|
action: () => this._umap.share.download(format),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
menu.openBelow(element, items)
|
menu.openBelow(element, items)
|
||||||
|
@ -250,10 +251,10 @@ export default class Browser {
|
||||||
// If at least one layer is shown, hide it
|
// If at least one layer is shown, hide it
|
||||||
// otherwise show all
|
// otherwise show all
|
||||||
let allHidden = true
|
let allHidden = true
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
if (datalayer.isVisible()) allHidden = false
|
if (datalayer.isVisible()) allHidden = false
|
||||||
})
|
})
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
if (allHidden) {
|
if (allHidden) {
|
||||||
datalayer.show()
|
datalayer.show()
|
||||||
} else {
|
} else {
|
||||||
|
@ -262,7 +263,7 @@ export default class Browser {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
static backButton(map) {
|
static backButton(umap) {
|
||||||
const button = DomUtil.createButtonIcon(
|
const button = DomUtil.createButtonIcon(
|
||||||
DomUtil.create('li', '', undefined),
|
DomUtil.create('li', '', undefined),
|
||||||
'icon-back',
|
'icon-back',
|
||||||
|
@ -271,7 +272,7 @@ export default class Browser {
|
||||||
// Fixme: remove me when this is merged and released
|
// Fixme: remove me when this is merged and released
|
||||||
// https://github.com/Leaflet/Leaflet/pull/9052
|
// https://github.com/Leaflet/Leaflet/pull/9052
|
||||||
DomEvent.disableClickPropagation(button)
|
DomEvent.disableClickPropagation(button)
|
||||||
DomEvent.on(button, 'click', map.umap.openBrowser, map.umap)
|
DomEvent.on(button, 'click', () => umap.openBrowser())
|
||||||
return button
|
return button
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,8 +3,9 @@ import { translate } from './i18n.js'
|
||||||
import * as Utils from './utils.js'
|
import * as Utils from './utils.js'
|
||||||
|
|
||||||
export default class Caption {
|
export default class Caption {
|
||||||
constructor(umap) {
|
constructor(umap, leafletMap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
|
this._leafletMap = leafletMap
|
||||||
}
|
}
|
||||||
|
|
||||||
isOpen() {
|
isOpen() {
|
||||||
|
@ -21,30 +22,30 @@ export default class Caption {
|
||||||
const hgroup = DomUtil.element({ tagName: 'hgroup', parent: container })
|
const hgroup = DomUtil.element({ tagName: 'hgroup', parent: container })
|
||||||
DomUtil.createTitle(
|
DomUtil.createTitle(
|
||||||
hgroup,
|
hgroup,
|
||||||
this.umap.getDisplayName(),
|
this._umap.getDisplayName(),
|
||||||
'icon-caption icon-block',
|
'icon-caption icon-block',
|
||||||
'map-name'
|
'map-name'
|
||||||
)
|
)
|
||||||
const title = Utils.loadTemplate('<h4></h4>')
|
const title = Utils.loadTemplate('<h4></h4>')
|
||||||
hgroup.appendChild(title)
|
hgroup.appendChild(title)
|
||||||
this.umap.addAuthorLink(title)
|
this._umap.addAuthorLink(title)
|
||||||
if (this.umap.properties.description) {
|
if (this._umap.properties.description) {
|
||||||
const description = DomUtil.element({
|
const description = DomUtil.element({
|
||||||
tagName: 'div',
|
tagName: 'div',
|
||||||
className: 'umap-map-description text',
|
className: 'umap-map-description text',
|
||||||
safeHTML: Utils.toHTML(this.umap.properties.description),
|
safeHTML: Utils.toHTML(this._umap.properties.description),
|
||||||
parent: container,
|
parent: container,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
const datalayerContainer = DomUtil.create('div', 'datalayer-container', container)
|
const datalayerContainer = DomUtil.create('div', 'datalayer-container', container)
|
||||||
this.umap.eachDataLayerReverse((datalayer) =>
|
this._umap.eachDataLayerReverse((datalayer) =>
|
||||||
this.addDataLayer(datalayer, datalayerContainer)
|
this.addDataLayer(datalayer, datalayerContainer)
|
||||||
)
|
)
|
||||||
const creditsContainer = DomUtil.create('div', 'credits-container', container)
|
const creditsContainer = DomUtil.create('div', 'credits-container', container)
|
||||||
this.addCredits(creditsContainer)
|
this.addCredits(creditsContainer)
|
||||||
this.umap.panel.open({ content: container }).then(() => {
|
this._umap.panel.open({ content: container }).then(() => {
|
||||||
// Create the legend when the panel is actually on the DOM
|
// Create the legend when the panel is actually on the DOM
|
||||||
this.umap.eachDataLayerReverse((datalayer) => datalayer.renderLegend())
|
this._umap.eachDataLayerReverse((datalayer) => datalayer.renderLegend())
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -67,16 +68,16 @@ export default class Caption {
|
||||||
addCredits(container) {
|
addCredits(container) {
|
||||||
const credits = DomUtil.createFieldset(container, translate('Credits'))
|
const credits = DomUtil.createFieldset(container, translate('Credits'))
|
||||||
let title = DomUtil.add('h5', '', credits, translate('User content credits'))
|
let title = DomUtil.add('h5', '', credits, translate('User content credits'))
|
||||||
if (this.umap.properties.shortCredit || this.umap.properties.longCredit) {
|
if (this._umap.properties.shortCredit || this._umap.properties.longCredit) {
|
||||||
DomUtil.element({
|
DomUtil.element({
|
||||||
tagName: 'p',
|
tagName: 'p',
|
||||||
parent: credits,
|
parent: credits,
|
||||||
safeHTML: Utils.toHTML(
|
safeHTML: Utils.toHTML(
|
||||||
this.umap.properties.longCredit || this.umap.properties.shortCredit
|
this._umap.properties.longCredit || this._umap.properties.shortCredit
|
||||||
),
|
),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
if (this.umap.properties.licence) {
|
if (this._umap.properties.licence) {
|
||||||
const licence = DomUtil.add(
|
const licence = DomUtil.add(
|
||||||
'p',
|
'p',
|
||||||
'',
|
'',
|
||||||
|
@ -86,8 +87,8 @@ export default class Caption {
|
||||||
DomUtil.createLink(
|
DomUtil.createLink(
|
||||||
'',
|
'',
|
||||||
licence,
|
licence,
|
||||||
this.umap.properties.licence.name,
|
this._umap.properties.licence.name,
|
||||||
this.umap.properties.licence.url
|
this._umap.properties.licence.url
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
DomUtil.add('p', '', credits, translate('No licence has been set'))
|
DomUtil.add('p', '', credits, translate('No licence has been set'))
|
||||||
|
@ -98,19 +99,19 @@ export default class Caption {
|
||||||
DomUtil.element({
|
DomUtil.element({
|
||||||
tagName: 'strong',
|
tagName: 'strong',
|
||||||
parent: tilelayerCredit,
|
parent: tilelayerCredit,
|
||||||
textContent: `${this.umap._leafletMap.selectedTilelayer.options.name} `,
|
textContent: `${this._leafletMap.selectedTilelayer.options.name} `,
|
||||||
})
|
})
|
||||||
DomUtil.element({
|
DomUtil.element({
|
||||||
tagName: 'span',
|
tagName: 'span',
|
||||||
parent: tilelayerCredit,
|
parent: tilelayerCredit,
|
||||||
safeHTML: this.umap._leafletMap.selectedTilelayer.getAttribution(),
|
safeHTML: this._leafletMap.selectedTilelayer.getAttribution(),
|
||||||
})
|
})
|
||||||
const urls = {
|
const urls = {
|
||||||
leaflet: 'http://leafletjs.com',
|
leaflet: 'http://leafletjs.com',
|
||||||
django: 'https://www.djangoproject.com',
|
django: 'https://www.djangoproject.com',
|
||||||
umap: 'https://umap-project.org/',
|
umap: 'https://umap-project.org/',
|
||||||
changelog: 'https://docs.umap-project.org/en/master/changelog/',
|
changelog: 'https://docs.umap-project.org/en/master/changelog/',
|
||||||
version: this.umap.properties.umap_version,
|
version: this._umap.properties.umap_version,
|
||||||
}
|
}
|
||||||
const creditHTML = translate(
|
const creditHTML = translate(
|
||||||
`
|
`
|
||||||
|
|
|
@ -18,8 +18,9 @@ import {
|
||||||
import loadPopup from '../rendering/popup.js'
|
import loadPopup from '../rendering/popup.js'
|
||||||
|
|
||||||
class Feature {
|
class Feature {
|
||||||
constructor(datalayer, geojson = {}, id = null) {
|
constructor(umap, datalayer, geojson = {}, id = null) {
|
||||||
this.sync = datalayer.umap.sync_engine.proxy(this)
|
this._umap = umap
|
||||||
|
this.sync = umap.sync_engine.proxy(this)
|
||||||
this._marked_for_deletion = false
|
this._marked_for_deletion = false
|
||||||
this._isDirty = false
|
this._isDirty = false
|
||||||
this._ui = null
|
this._ui = null
|
||||||
|
@ -69,10 +70,6 @@ class Feature {
|
||||||
return this._ui
|
return this._ui
|
||||||
}
|
}
|
||||||
|
|
||||||
get umap() {
|
|
||||||
return this.datalayer?.umap
|
|
||||||
}
|
|
||||||
|
|
||||||
get center() {
|
get center() {
|
||||||
return this.ui.getCenter()
|
return this.ui.getCenter()
|
||||||
}
|
}
|
||||||
|
@ -168,7 +165,7 @@ class Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
getSlug() {
|
getSlug() {
|
||||||
return this.properties[this.umap.getOption('slugKey') || 'name'] || ''
|
return this.properties[this._umap.getProperty('slugKey') || 'name'] || ''
|
||||||
}
|
}
|
||||||
|
|
||||||
getPermalink() {
|
getPermalink() {
|
||||||
|
@ -196,10 +193,10 @@ class Feature {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
// TODO deal with an event instead?
|
// TODO deal with an event instead?
|
||||||
if (this.umap.slideshow) {
|
if (this._umap.slideshow) {
|
||||||
this.umap.slideshow.current = this
|
this._umap.slideshow.current = this
|
||||||
}
|
}
|
||||||
this.umap.currentFeature = this
|
this._umap.currentFeature = this
|
||||||
this.attachPopup()
|
this.attachPopup()
|
||||||
this.ui.openPopup(latlng || this.center)
|
this.ui.openPopup(latlng || this.center)
|
||||||
}
|
}
|
||||||
|
@ -209,7 +206,7 @@ class Feature {
|
||||||
return field.startsWith('properties.')
|
return field.startsWith('properties.')
|
||||||
})
|
})
|
||||||
if (impactData) {
|
if (impactData) {
|
||||||
if (this.umap.currentFeature === this) {
|
if (this._umap.currentFeature === this) {
|
||||||
this.view()
|
this.view()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -217,7 +214,7 @@ class Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
edit(event) {
|
edit(event) {
|
||||||
if (!this.umap.editEnabled || this.isReadOnly()) return
|
if (!this._umap.editEnabled || this.isReadOnly()) return
|
||||||
const container = DomUtil.create('div', 'umap-feature-container')
|
const container = DomUtil.create('div', 'umap-feature-container')
|
||||||
DomUtil.createTitle(
|
DomUtil.createTitle(
|
||||||
container,
|
container,
|
||||||
|
@ -256,12 +253,12 @@ class Feature {
|
||||||
translate('Advanced actions')
|
translate('Advanced actions')
|
||||||
)
|
)
|
||||||
this.getAdvancedEditActions(advancedActions)
|
this.getAdvancedEditActions(advancedActions)
|
||||||
const onLoad = this.umap.editPanel.open({ content: container })
|
const onLoad = this._umap.editPanel.open({ content: container })
|
||||||
onLoad.then(() => {
|
onLoad.then(() => {
|
||||||
builder.helpers['properties.name'].input.focus()
|
builder.helpers['properties.name'].input.focus()
|
||||||
})
|
})
|
||||||
this.umap.editedFeature = this
|
this._umap.editedFeature = this
|
||||||
if (!this.ui.isOnScreen(this.umap._leafletMap.getBounds())) this.zoomTo(event)
|
if (!this.ui.isOnScreen(this._umap._leafletMap.getBounds())) this.zoomTo(event)
|
||||||
}
|
}
|
||||||
|
|
||||||
getAdvancedEditActions(container) {
|
getAdvancedEditActions(container) {
|
||||||
|
@ -270,7 +267,7 @@ class Feature {
|
||||||
<i class="icon icon-24 icon-delete"></i>${translate('Delete')}
|
<i class="icon icon-24 icon-delete"></i>${translate('Delete')}
|
||||||
</button>`)
|
</button>`)
|
||||||
button.addEventListener('click', () => {
|
button.addEventListener('click', () => {
|
||||||
this.confirmDelete().then(() => this.umap.editPanel.close())
|
this.confirmDelete().then(() => this._umap.editPanel.close())
|
||||||
})
|
})
|
||||||
container.appendChild(button)
|
container.appendChild(button)
|
||||||
}
|
}
|
||||||
|
@ -320,20 +317,25 @@ class Feature {
|
||||||
endEdit() {}
|
endEdit() {}
|
||||||
|
|
||||||
getDisplayName(fallback) {
|
getDisplayName(fallback) {
|
||||||
if (fallback === undefined) fallback = this.datalayer.getName()
|
|
||||||
const key = this.getOption('labelKey') || 'name'
|
const key = this.getOption('labelKey') || 'name'
|
||||||
// Variables mode.
|
// Variables mode.
|
||||||
if (U.Utils.hasVar(key))
|
if (Utils.hasVar(key)) {
|
||||||
return U.Utils.greedyTemplate(key, this.extendedProperties())
|
return Utils.greedyTemplate(key, this.extendedProperties())
|
||||||
|
}
|
||||||
// Simple mode.
|
// Simple mode.
|
||||||
return this.properties[key] || this.properties.title || fallback
|
return (
|
||||||
|
this.properties[key] ||
|
||||||
|
this.properties.title ||
|
||||||
|
fallback ||
|
||||||
|
this.datalayer.getName()
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
hasPopupFooter() {
|
hasPopupFooter() {
|
||||||
if (this.datalayer.isRemoteLayer() && this.datalayer.options.remoteData.dynamic) {
|
if (this.datalayer.isRemoteLayer() && this.datalayer.options.remoteData.dynamic) {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
return this.umap.getOption('displayPopupFooter')
|
return this._umap.getProperty('displayPopupFooter')
|
||||||
}
|
}
|
||||||
|
|
||||||
getPopupClass() {
|
getPopupClass() {
|
||||||
|
@ -347,7 +349,7 @@ class Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
async confirmDelete() {
|
async confirmDelete() {
|
||||||
const confirmed = await this.umap.dialog.confirm(
|
const confirmed = await this._umap.dialog.confirm(
|
||||||
translate('Are you sure you want to delete the feature?')
|
translate('Are you sure you want to delete the feature?')
|
||||||
)
|
)
|
||||||
if (confirmed) {
|
if (confirmed) {
|
||||||
|
@ -359,7 +361,7 @@ class Feature {
|
||||||
|
|
||||||
del(sync) {
|
del(sync) {
|
||||||
this.isDirty = true
|
this.isDirty = true
|
||||||
this.umap._leafletMap.closePopup()
|
this._umap._leafletMap.closePopup()
|
||||||
if (this.datalayer) {
|
if (this.datalayer) {
|
||||||
this.datalayer.removeFeature(this, sync)
|
this.datalayer.removeFeature(this, sync)
|
||||||
}
|
}
|
||||||
|
@ -417,34 +419,37 @@ class Feature {
|
||||||
let value = fallback
|
let value = fallback
|
||||||
if (typeof this.staticOptions[option] !== 'undefined') {
|
if (typeof this.staticOptions[option] !== 'undefined') {
|
||||||
value = this.staticOptions[option]
|
value = this.staticOptions[option]
|
||||||
} else if (U.Utils.usableOption(this.properties._umap_options, option)) {
|
} else if (Utils.usableOption(this.properties._umap_options, option)) {
|
||||||
value = this.properties._umap_options[option]
|
value = this.properties._umap_options[option]
|
||||||
} else if (this.datalayer) {
|
} else if (this.datalayer) {
|
||||||
value = this.datalayer.getOption(option, this)
|
value = this.datalayer.getOption(option, this)
|
||||||
} else {
|
} else {
|
||||||
value = this.umap.getOption(option)
|
value = this._umap.getProperty(option)
|
||||||
}
|
}
|
||||||
return value
|
return value
|
||||||
}
|
}
|
||||||
|
|
||||||
getDynamicOption(option, fallback) {
|
getDynamicOption(key, fallback) {
|
||||||
let value = this.getOption(option, fallback)
|
let value = this.getOption(key, fallback)
|
||||||
// There is a variable inside.
|
// There is a variable inside.
|
||||||
if (U.Utils.hasVar(value)) {
|
if (Utils.hasVar(value)) {
|
||||||
value = U.Utils.greedyTemplate(value, this.properties, true)
|
value = Utils.greedyTemplate(value, this.properties, true)
|
||||||
if (U.Utils.hasVar(value)) value = this.umap.getDefaultOption(option)
|
if (Utils.hasVar(value)) value = SCHEMA[key]?.default
|
||||||
}
|
}
|
||||||
return value
|
return value
|
||||||
}
|
}
|
||||||
|
|
||||||
zoomTo({ easing, latlng, callback } = {}) {
|
zoomTo({ easing, latlng, callback } = {}) {
|
||||||
if (easing === undefined) easing = this.umap.getOption('easing')
|
if (easing === undefined) easing = this._umap.getProperty('easing')
|
||||||
if (callback) this.umap._leafletMap.once('moveend', callback.bind(this))
|
if (callback) this._umap._leafletMap.once('moveend', callback.bind(this))
|
||||||
if (easing) {
|
if (easing) {
|
||||||
this.umap._leafletMap.flyTo(this.center, this.getBestZoom())
|
this._umap._leafletMap.flyTo(this.center, this.getBestZoom())
|
||||||
} else {
|
} else {
|
||||||
latlng = latlng || this.center
|
latlng = latlng || this.center
|
||||||
this.umap._leafletMap.setView(latlng, this.getBestZoom() || this.umap._leafletMap.getZoom())
|
this._umap._leafletMap.setView(
|
||||||
|
latlng,
|
||||||
|
this.getBestZoom() || this._umap._leafletMap.getZoom()
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -494,13 +499,9 @@ class Feature {
|
||||||
return [U.ToggleEditAction, U.DeleteFeatureAction]
|
return [U.ToggleEditAction, U.DeleteFeatureAction]
|
||||||
}
|
}
|
||||||
|
|
||||||
getMap() {
|
|
||||||
return this.map
|
|
||||||
}
|
|
||||||
|
|
||||||
isFiltered() {
|
isFiltered() {
|
||||||
const filterKeys = this.datalayer.getFilterKeys()
|
const filterKeys = this.datalayer.getFilterKeys()
|
||||||
const filter = this.umap.browser.options.filter
|
const filter = this._umap.browser.options.filter
|
||||||
if (filter && !this.matchFilter(filter, filterKeys)) return true
|
if (filter && !this.matchFilter(filter, filterKeys)) return true
|
||||||
if (!this.matchFacets()) return true
|
if (!this.matchFacets()) return true
|
||||||
return false
|
return false
|
||||||
|
@ -525,10 +526,10 @@ class Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
matchFacets() {
|
matchFacets() {
|
||||||
const selected = this.umap.facets.selected
|
const selected = this._umap.facets.selected
|
||||||
for (const [name, { type, min, max, choices }] of Object.entries(selected)) {
|
for (const [name, { type, min, max, choices }] of Object.entries(selected)) {
|
||||||
let value = this.properties[name]
|
let value = this.properties[name]
|
||||||
const parser = this.umap.facets.getParser(type)
|
const parser = this._umap.facets.getParser(type)
|
||||||
value = parser(value)
|
value = parser(value)
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case 'date':
|
case 'date':
|
||||||
|
@ -562,7 +563,7 @@ class Feature {
|
||||||
|
|
||||||
extendedProperties() {
|
extendedProperties() {
|
||||||
// Include context properties
|
// Include context properties
|
||||||
const properties = this.umap.getGeoContext()
|
const properties = this._umap.getGeoContext()
|
||||||
const locale = L.getLocale()
|
const locale = L.getLocale()
|
||||||
if (locale) properties.locale = locale
|
if (locale) properties.locale = locale
|
||||||
if (U.lang) properties.lang = U.lang
|
if (U.lang) properties.lang = U.lang
|
||||||
|
@ -612,10 +613,10 @@ class Feature {
|
||||||
label: translate('Copy as GeoJSON'),
|
label: translate('Copy as GeoJSON'),
|
||||||
action: () => {
|
action: () => {
|
||||||
L.Util.copyToClipboard(JSON.stringify(this.toGeoJSON()))
|
L.Util.copyToClipboard(JSON.stringify(this.toGeoJSON()))
|
||||||
this.umap.tooltip.open({ content: L._('✅ Copied!') })
|
this._umap.tooltip.open({ content: L._('✅ Copied!') })
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
if (this.umap.editEnabled && !this.isReadOnly()) {
|
if (this._umap.editEnabled && !this.isReadOnly()) {
|
||||||
items = items.concat(this.getContextMenuEditItems(event))
|
items = items.concat(this.getContextMenuEditItems(event))
|
||||||
}
|
}
|
||||||
return items
|
return items
|
||||||
|
@ -623,7 +624,7 @@ class Feature {
|
||||||
|
|
||||||
getContextMenuEditItems() {
|
getContextMenuEditItems() {
|
||||||
let items = ['-']
|
let items = ['-']
|
||||||
if (this.umap.editedFeature !== this) {
|
if (this._umap.editedFeature !== this) {
|
||||||
items.push({
|
items.push({
|
||||||
label: `${translate('Edit this feature')} (⇧+Click)`,
|
label: `${translate('Edit this feature')} (⇧+Click)`,
|
||||||
action: () => this.edit(),
|
action: () => this.edit(),
|
||||||
|
@ -631,7 +632,7 @@ class Feature {
|
||||||
}
|
}
|
||||||
items = items.concat(
|
items = items.concat(
|
||||||
{
|
{
|
||||||
label: this.umap.help.displayLabel('EDIT_FEATURE_LAYER'),
|
label: this._umap.help.displayLabel('EDIT_FEATURE_LAYER'),
|
||||||
action: () => this.datalayer.edit(),
|
action: () => this.datalayer.edit(),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -648,8 +649,8 @@ class Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Point extends Feature {
|
export class Point extends Feature {
|
||||||
constructor(datalayer, geojson, id) {
|
constructor(umap, datalayer, geojson, id) {
|
||||||
super(datalayer, geojson, id)
|
super(umap, datalayer, geojson, id)
|
||||||
this.staticOptions = {
|
this.staticOptions = {
|
||||||
mainColor: 'color',
|
mainColor: 'color',
|
||||||
className: 'marker',
|
className: 'marker',
|
||||||
|
@ -750,17 +751,17 @@ class Path extends Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
edit(event) {
|
edit(event) {
|
||||||
if (this.umap.editEnabled) {
|
if (this._umap.editEnabled) {
|
||||||
super.edit(event)
|
super.edit(event)
|
||||||
if (!this.ui.editEnabled()) this.ui.makeGeometryEditable()
|
if (!this.ui.editEnabled()) this.ui.makeGeometryEditable()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_toggleEditing(event) {
|
_toggleEditing(event) {
|
||||||
if (this.umap.editEnabled) {
|
if (this._umap.editEnabled) {
|
||||||
if (this.ui.editEnabled()) {
|
if (this.ui.editEnabled()) {
|
||||||
this.endEdit()
|
this.endEdit()
|
||||||
this.umap.editPanel.close()
|
this._umap.editPanel.close()
|
||||||
} else {
|
} else {
|
||||||
this.edit(event)
|
this.edit(event)
|
||||||
}
|
}
|
||||||
|
@ -787,7 +788,8 @@ class Path extends Feature {
|
||||||
|
|
||||||
getBestZoom() {
|
getBestZoom() {
|
||||||
return (
|
return (
|
||||||
this.getOption('zoomTo') || this.umap._leafletMap.getBoundsZoom(this.bounds, true)
|
this.getOption('zoomTo') ||
|
||||||
|
this._umap._leafletMap.getBoundsZoom(this.bounds, true)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -827,13 +829,13 @@ class Path extends Feature {
|
||||||
|
|
||||||
zoomTo({ easing, callback }) {
|
zoomTo({ easing, callback }) {
|
||||||
// Use bounds instead of centroid for paths.
|
// Use bounds instead of centroid for paths.
|
||||||
easing = easing || this.umap.getOption('easing')
|
easing = easing || this._umap.getProperty('easing')
|
||||||
if (easing) {
|
if (easing) {
|
||||||
this.umap._leafletMap.flyToBounds(this.bounds, this.getBestZoom())
|
this._umap._leafletMap.flyToBounds(this.bounds, this.getBestZoom())
|
||||||
} else {
|
} else {
|
||||||
this.umap._leafletMap.fitBounds(
|
this._umap._leafletMap.fitBounds(
|
||||||
this.bounds,
|
this.bounds,
|
||||||
this.getBestZoom() || this.umap._leafletMap.getZoom()
|
this.getBestZoom() || this._umap._leafletMap.getZoom()
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
if (callback) callback.call(this)
|
if (callback) callback.call(this)
|
||||||
|
@ -845,7 +847,7 @@ class Path extends Feature {
|
||||||
label: translate('Display measure'),
|
label: translate('Display measure'),
|
||||||
action: () => Alert.info(this.ui.getMeasure()),
|
action: () => Alert.info(this.ui.getMeasure()),
|
||||||
})
|
})
|
||||||
if (this.umap.editEnabled && !this.isReadOnly() && this.isMulti()) {
|
if (this._umap.editEnabled && !this.isReadOnly() && this.isMulti()) {
|
||||||
items.push(...this.getContextMenuMultiItems(event))
|
items.push(...this.getContextMenuMultiItems(event))
|
||||||
}
|
}
|
||||||
return items
|
return items
|
||||||
|
@ -876,11 +878,14 @@ class Path extends Feature {
|
||||||
|
|
||||||
getContextMenuEditItems(event) {
|
getContextMenuEditItems(event) {
|
||||||
const items = super.getContextMenuEditItems(event)
|
const items = super.getContextMenuEditItems(event)
|
||||||
if (this.map?.editedFeature !== this && this.isSameClass(this.umap.editedFeature)) {
|
if (
|
||||||
|
this._umap?.editedFeature !== this &&
|
||||||
|
this.isSameClass(this._umap.editedFeature)
|
||||||
|
) {
|
||||||
items.push({
|
items.push({
|
||||||
label: translate('Transfer shape to edited feature'),
|
label: translate('Transfer shape to edited feature'),
|
||||||
action: () => {
|
action: () => {
|
||||||
this.transferShape(event.latlng, this.umap.editedFeature)
|
this.transferShape(event.latlng, this._umap.editedFeature)
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -897,8 +902,8 @@ class Path extends Feature {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class LineString extends Path {
|
export class LineString extends Path {
|
||||||
constructor(datalayer, geojson, id) {
|
constructor(umap, datalayer, geojson, id) {
|
||||||
super(datalayer, geojson, id)
|
super(umap, datalayer, geojson, id)
|
||||||
this.staticOptions = {
|
this.staticOptions = {
|
||||||
stroke: true,
|
stroke: true,
|
||||||
fill: false,
|
fill: false,
|
||||||
|
@ -982,8 +987,8 @@ export class LineString extends Path {
|
||||||
}
|
}
|
||||||
const a = toMerge[0]
|
const a = toMerge[0]
|
||||||
const b = toMerge[1]
|
const b = toMerge[1]
|
||||||
const p1 = this.umap._leafletMap.latLngToContainerPoint(a[a.length - 1])
|
const p1 = this._umap._leafletMap.latLngToContainerPoint(a[a.length - 1])
|
||||||
const p2 = this.umap._leafletMap.latLngToContainerPoint(b[0])
|
const p2 = this._umap._leafletMap.latLngToContainerPoint(b[0])
|
||||||
const tolerance = 5 // px on screen
|
const tolerance = 5 // px on screen
|
||||||
if (Math.abs(p1.x - p2.x) <= tolerance && Math.abs(p1.y - p2.y) <= tolerance) {
|
if (Math.abs(p1.x - p2.x) <= tolerance && Math.abs(p1.y - p2.y) <= tolerance) {
|
||||||
a.pop()
|
a.pop()
|
||||||
|
@ -1027,7 +1032,7 @@ export class LineString extends Path {
|
||||||
})
|
})
|
||||||
} else if (index === 0 || index === event.vertex.getLastIndex()) {
|
} else if (index === 0 || index === event.vertex.getLastIndex()) {
|
||||||
items.push({
|
items.push({
|
||||||
label: this.umap.help.displayLabel('CONTINUE_LINE'),
|
label: this._umap.help.displayLabel('CONTINUE_LINE'),
|
||||||
action: () => event.vertex.continue(),
|
action: () => event.vertex.continue(),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -1046,8 +1051,8 @@ export class LineString extends Path {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Polygon extends Path {
|
export class Polygon extends Path {
|
||||||
constructor(datalayer, geojson, id) {
|
constructor(umap, datalayer, geojson, id) {
|
||||||
super(datalayer, geojson, id)
|
super(umap, datalayer, geojson, id)
|
||||||
this.staticOptions = {
|
this.staticOptions = {
|
||||||
mainColor: 'fillColor',
|
mainColor: 'fillColor',
|
||||||
className: 'polygon',
|
className: 'polygon',
|
||||||
|
|
|
@ -21,6 +21,7 @@ import { DataLayerPermissions } from '../permissions.js'
|
||||||
import { Point, LineString, Polygon } from './features.js'
|
import { Point, LineString, Polygon } from './features.js'
|
||||||
import TableEditor from '../tableeditor.js'
|
import TableEditor from '../tableeditor.js'
|
||||||
import { ServerStored } from '../saving.js'
|
import { ServerStored } from '../saving.js'
|
||||||
|
import * as Schema from '../schema.js'
|
||||||
|
|
||||||
export const LAYER_TYPES = [
|
export const LAYER_TYPES = [
|
||||||
DefaultLayer,
|
DefaultLayer,
|
||||||
|
@ -37,9 +38,9 @@ const LAYER_MAP = LAYER_TYPES.reduce((acc, klass) => {
|
||||||
}, {})
|
}, {})
|
||||||
|
|
||||||
export class DataLayer extends ServerStored {
|
export class DataLayer extends ServerStored {
|
||||||
constructor(umap, data) {
|
constructor(umap, leafletMap, data) {
|
||||||
super()
|
super()
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.sync = umap.sync_engine.proxy(this)
|
this.sync = umap.sync_engine.proxy(this)
|
||||||
this._index = Array()
|
this._index = Array()
|
||||||
this._features = {}
|
this._features = {}
|
||||||
|
@ -48,8 +49,9 @@ export class DataLayer extends ServerStored {
|
||||||
this._loaded = false // Are layer metadata loaded
|
this._loaded = false // Are layer metadata loaded
|
||||||
this._dataloaded = false // Are layer data loaded
|
this._dataloaded = false // Are layer data loaded
|
||||||
|
|
||||||
this.parentPane = this.umap._leafletMap.getPane('overlayPane')
|
this._leafletMap = leafletMap
|
||||||
this.pane = this.umap._leafletMap.createPane(
|
this.parentPane = this._leafletMap.getPane('overlayPane')
|
||||||
|
this.pane = this._leafletMap.createPane(
|
||||||
`datalayer${stamp(this)}`,
|
`datalayer${stamp(this)}`,
|
||||||
this.parentPane
|
this.parentPane
|
||||||
)
|
)
|
||||||
|
@ -81,7 +83,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
this.backupOptions()
|
this.backupOptions()
|
||||||
this.connectToMap()
|
this.connectToMap()
|
||||||
this.permissions = new DataLayerPermissions(this)
|
this.permissions = new DataLayerPermissions(this._umap, this)
|
||||||
if (!this.umap_id) {
|
if (!this.umap_id) {
|
||||||
if (this.showAtLoad()) this.show()
|
if (this.showAtLoad()) this.show()
|
||||||
this.isDirty = true
|
this.isDirty = true
|
||||||
|
@ -131,7 +133,7 @@ export class DataLayer extends ServerStored {
|
||||||
for (const impact of impacts) {
|
for (const impact of impacts) {
|
||||||
switch (impact) {
|
switch (impact) {
|
||||||
case 'ui':
|
case 'ui':
|
||||||
this.umap.onDataLayersChanged()
|
this._umap.onDataLayersChanged()
|
||||||
break
|
break
|
||||||
case 'data':
|
case 'data':
|
||||||
if (fields.includes('options.type')) {
|
if (fields.includes('options.type')) {
|
||||||
|
@ -156,8 +158,8 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
autoLoaded() {
|
autoLoaded() {
|
||||||
if (!this.umap.datalayersFromQueryString) return this.options.displayOnLoad
|
if (!this._umap.datalayersFromQueryString) return this.options.displayOnLoad
|
||||||
const datalayerIds = this.umap.datalayersFromQueryString
|
const datalayerIds = this._umap.datalayersFromQueryString
|
||||||
let loadMe = datalayerIds.includes(this.umap_id.toString())
|
let loadMe = datalayerIds.includes(this.umap_id.toString())
|
||||||
if (this.options.old_id) {
|
if (this.options.old_id) {
|
||||||
loadMe = loadMe || datalayerIds.includes(this.options.old_id.toString())
|
loadMe = loadMe || datalayerIds.includes(this.options.old_id.toString())
|
||||||
|
@ -195,7 +197,7 @@ export class DataLayer extends ServerStored {
|
||||||
const visible = this.isVisible()
|
const visible = this.isVisible()
|
||||||
if (this.layer) this.layer.clearLayers()
|
if (this.layer) this.layer.clearLayers()
|
||||||
// delete this.layer?
|
// delete this.layer?
|
||||||
if (visible) this.umap._leafletMap.removeLayer(this.layer)
|
if (visible) this._leafletMap.removeLayer(this.layer)
|
||||||
const Class = LAYER_MAP[this.options.type] || DefaultLayer
|
const Class = LAYER_MAP[this.options.type] || DefaultLayer
|
||||||
this.layer = new Class(this)
|
this.layer = new Class(this)
|
||||||
// Rendering layer changed, so let's force reset the feature rendering too.
|
// Rendering layer changed, so let's force reset the feature rendering too.
|
||||||
|
@ -216,7 +218,7 @@ export class DataLayer extends ServerStored {
|
||||||
if (!this.umap_id) return
|
if (!this.umap_id) return
|
||||||
if (this._loading) return
|
if (this._loading) return
|
||||||
this._loading = true
|
this._loading = true
|
||||||
const [geojson, response, error] = await this.umap.server.get(this._dataUrl())
|
const [geojson, response, error] = await this._umap.server.get(this._dataUrl())
|
||||||
if (!error) {
|
if (!error) {
|
||||||
this._reference_version = response.headers.get('X-Datalayer-Version')
|
this._reference_version = response.headers.get('X-Datalayer-Version')
|
||||||
// FIXME: for now this property is set dynamically from backend
|
// FIXME: for now this property is set dynamically from backend
|
||||||
|
@ -237,7 +239,7 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
dataChanged() {
|
dataChanged() {
|
||||||
if (!this.hasDataLoaded()) return
|
if (!this.hasDataLoaded()) return
|
||||||
this.umap.onDataLayersChanged()
|
this._umap.onDataLayersChanged()
|
||||||
this.layer.dataChanged()
|
this.layer.dataChanged()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -278,14 +280,14 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
reindex() {
|
reindex() {
|
||||||
const features = Object.values(this._features)
|
const features = Object.values(this._features)
|
||||||
Utils.sortFeatures(features, this.umap.getOption('sortKey'), U.lang)
|
Utils.sortFeatures(features, this._umap.getProperty('sortKey'), U.lang)
|
||||||
this._index = features.map((feature) => stamp(feature))
|
this._index = features.map((feature) => stamp(feature))
|
||||||
}
|
}
|
||||||
|
|
||||||
showAtZoom() {
|
showAtZoom() {
|
||||||
const from = Number.parseInt(this.options.fromZoom, 10)
|
const from = Number.parseInt(this.options.fromZoom, 10)
|
||||||
const to = Number.parseInt(this.options.toZoom, 10)
|
const to = Number.parseInt(this.options.toZoom, 10)
|
||||||
const zoom = this.umap._leafletMap.getZoom()
|
const zoom = this._leafletMap.getZoom()
|
||||||
return !((!Number.isNaN(from) && zoom < from) || (!Number.isNaN(to) && zoom > to))
|
return !((!Number.isNaN(from) && zoom < from) || (!Number.isNaN(to) && zoom > to))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -297,14 +299,14 @@ export class DataLayer extends ServerStored {
|
||||||
if (!this.isRemoteLayer()) return
|
if (!this.isRemoteLayer()) return
|
||||||
if (!this.hasDynamicData() && this.hasDataLoaded() && !force) return
|
if (!this.hasDynamicData() && this.hasDataLoaded() && !force) return
|
||||||
if (!this.isVisible()) return
|
if (!this.isVisible()) return
|
||||||
let url = this.umap.localizeUrl(this.options.remoteData.url)
|
let url = this._umap.renderUrl(this.options.remoteData.url)
|
||||||
if (this.options.remoteData.proxy) {
|
if (this.options.remoteData.proxy) {
|
||||||
url = this.umap.proxyUrl(url, this.options.remoteData.ttl)
|
url = this._umap.proxyUrl(url, this.options.remoteData.ttl)
|
||||||
}
|
}
|
||||||
const response = await this.umap.request.get(url)
|
const response = await this._umap.request.get(url)
|
||||||
if (response?.ok) {
|
if (response?.ok) {
|
||||||
this.clear()
|
this.clear()
|
||||||
this.umap.formatter
|
this._umap.formatter
|
||||||
.parse(await response.text(), this.options.remoteData.format)
|
.parse(await response.text(), this.options.remoteData.format)
|
||||||
.then((geojson) => this.fromGeoJSON(geojson))
|
.then((geojson) => this.fromGeoJSON(geojson))
|
||||||
}
|
}
|
||||||
|
@ -344,23 +346,23 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
connectToMap() {
|
connectToMap() {
|
||||||
const id = stamp(this)
|
const id = stamp(this)
|
||||||
if (!this.umap.datalayers[id]) {
|
if (!this._umap.datalayers[id]) {
|
||||||
this.umap.datalayers[id] = this
|
this._umap.datalayers[id] = this
|
||||||
}
|
}
|
||||||
if (!this.umap.datalayersIndex.includes(this)) {
|
if (!this._umap.datalayersIndex.includes(this)) {
|
||||||
this.umap.datalayersIndex.push(this)
|
this._umap.datalayersIndex.push(this)
|
||||||
}
|
}
|
||||||
this.umap.onDataLayersChanged()
|
this._umap.onDataLayersChanged()
|
||||||
}
|
}
|
||||||
|
|
||||||
_dataUrl() {
|
_dataUrl() {
|
||||||
let url = this.umap.urls.get('datalayer_view', {
|
let url = this._umap.urls.get('datalayer_view', {
|
||||||
pk: this.umap_id,
|
pk: this.umap_id,
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
|
|
||||||
// No browser cache for owners/editors.
|
// No browser cache for owners/editors.
|
||||||
if (this.umap.hasEditMode()) url = `${url}?${Date.now()}`
|
if (this._umap.hasEditMode()) url = `${url}?${Date.now()}`
|
||||||
return url
|
return url
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -387,7 +389,7 @@ export class DataLayer extends ServerStored {
|
||||||
this._index.push(id)
|
this._index.push(id)
|
||||||
this._features[id] = feature
|
this._features[id] = feature
|
||||||
this.indexProperties(feature)
|
this.indexProperties(feature)
|
||||||
this.umap.featuresIndex[feature.getSlug()] = feature
|
this._umap.featuresIndex[feature.getSlug()] = feature
|
||||||
this.showFeature(feature)
|
this.showFeature(feature)
|
||||||
this.dataChanged()
|
this.dataChanged()
|
||||||
}
|
}
|
||||||
|
@ -396,7 +398,7 @@ export class DataLayer extends ServerStored {
|
||||||
const id = stamp(feature)
|
const id = stamp(feature)
|
||||||
if (sync !== false) feature.sync.delete()
|
if (sync !== false) feature.sync.delete()
|
||||||
this.hideFeature(feature)
|
this.hideFeature(feature)
|
||||||
delete this.umap.featuresIndex[feature.getSlug()]
|
delete this._umap.featuresIndex[feature.getSlug()]
|
||||||
feature.disconnectFromDataLayer(this)
|
feature.disconnectFromDataLayer(this)
|
||||||
this._index.splice(this._index.indexOf(id), 1)
|
this._index.splice(this._index.indexOf(id), 1)
|
||||||
delete this._features[id]
|
delete this._features[id]
|
||||||
|
@ -448,7 +450,7 @@ export class DataLayer extends ServerStored {
|
||||||
? geojson
|
? geojson
|
||||||
: geojson.features || geojson.geometries
|
: geojson.features || geojson.geometries
|
||||||
if (!collection) return
|
if (!collection) return
|
||||||
Utils.sortFeatures(collection, this.umap.getOption('sortKey'), U.lang)
|
Utils.sortFeatures(collection, this._umap.getProperty('sortKey'), U.lang)
|
||||||
for (const feature of collection) {
|
for (const feature of collection) {
|
||||||
this.makeFeature(feature, sync)
|
this.makeFeature(feature, sync)
|
||||||
}
|
}
|
||||||
|
@ -462,15 +464,15 @@ export class DataLayer extends ServerStored {
|
||||||
switch (geometry.type) {
|
switch (geometry.type) {
|
||||||
case 'Point':
|
case 'Point':
|
||||||
// FIXME: deal with MultiPoint
|
// FIXME: deal with MultiPoint
|
||||||
feature = new Point(this, geojson, id)
|
feature = new Point(this._umap, this, geojson, id)
|
||||||
break
|
break
|
||||||
case 'MultiLineString':
|
case 'MultiLineString':
|
||||||
case 'LineString':
|
case 'LineString':
|
||||||
feature = new LineString(this, geojson, id)
|
feature = new LineString(this._umap, this, geojson, id)
|
||||||
break
|
break
|
||||||
case 'MultiPolygon':
|
case 'MultiPolygon':
|
||||||
case 'Polygon':
|
case 'Polygon':
|
||||||
feature = new Polygon(this, geojson, id)
|
feature = new Polygon(this._umap, this, geojson, id)
|
||||||
break
|
break
|
||||||
default:
|
default:
|
||||||
console.log(geojson)
|
console.log(geojson)
|
||||||
|
@ -488,7 +490,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
async importRaw(raw, format) {
|
async importRaw(raw, format) {
|
||||||
this.umap.formatter
|
this._umap.formatter
|
||||||
.parse(raw, format)
|
.parse(raw, format)
|
||||||
.then((geojson) => this.addData(geojson))
|
.then((geojson) => this.addData(geojson))
|
||||||
.then(() => this.zoomTo())
|
.then(() => this.zoomTo())
|
||||||
|
@ -509,35 +511,35 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
async importFromUrl(uri, type) {
|
async importFromUrl(uri, type) {
|
||||||
uri = this.umap.localizeUrl(uri)
|
uri = this._umap.renderUrl(uri)
|
||||||
const response = await this.umap.request.get(uri)
|
const response = await this._umap.request.get(uri)
|
||||||
if (response?.ok) {
|
if (response?.ok) {
|
||||||
this.importRaw(await response.text(), type)
|
this.importRaw(await response.text(), type)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getColor() {
|
getColor() {
|
||||||
return this.options.color || this.umap.getOption('color')
|
return this.options.color || this._umap.getProperty('color')
|
||||||
}
|
}
|
||||||
|
|
||||||
getDeleteUrl() {
|
getDeleteUrl() {
|
||||||
return this.umap.urls.get('datalayer_delete', {
|
return this._umap.urls.get('datalayer_delete', {
|
||||||
pk: this.umap_id,
|
pk: this.umap_id,
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
getVersionsUrl() {
|
getVersionsUrl() {
|
||||||
return this.umap.urls.get('datalayer_versions', {
|
return this._umap.urls.get('datalayer_versions', {
|
||||||
pk: this.umap_id,
|
pk: this.umap_id,
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
getVersionUrl(name) {
|
getVersionUrl(name) {
|
||||||
return this.umap.urls.get('datalayer_version', {
|
return this._umap.urls.get('datalayer_version', {
|
||||||
pk: this.umap_id,
|
pk: this.umap_id,
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
name: name,
|
name: name,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -558,17 +560,17 @@ export class DataLayer extends ServerStored {
|
||||||
options.name = translate('Clone of {name}', { name: this.options.name })
|
options.name = translate('Clone of {name}', { name: this.options.name })
|
||||||
delete options.id
|
delete options.id
|
||||||
const geojson = Utils.CopyJSON(this._geojson)
|
const geojson = Utils.CopyJSON(this._geojson)
|
||||||
const datalayer = this.umap.createDataLayer(options)
|
const datalayer = this._umap.createDataLayer(options)
|
||||||
datalayer.fromGeoJSON(geojson)
|
datalayer.fromGeoJSON(geojson)
|
||||||
return datalayer
|
return datalayer
|
||||||
}
|
}
|
||||||
|
|
||||||
erase() {
|
erase() {
|
||||||
this.hide()
|
this.hide()
|
||||||
this.umap.datalayersIndex.splice(this.getRank(), 1)
|
this._umap.datalayersIndex.splice(this.getRank(), 1)
|
||||||
this.parentPane.removeChild(this.pane)
|
this.parentPane.removeChild(this.pane)
|
||||||
this.umap.onDataLayersChanged()
|
this._umap.onDataLayersChanged()
|
||||||
this.layer.onDelete(this.umap._leafletMap)
|
this.layer.onDelete(this._leafletMap)
|
||||||
this.propagateDelete()
|
this.propagateDelete()
|
||||||
this._leaflet_events_bk = this._leaflet_events
|
this._leaflet_events_bk = this._leaflet_events
|
||||||
this.clear()
|
this.clear()
|
||||||
|
@ -599,7 +601,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
edit() {
|
edit() {
|
||||||
if (!this.umap.editEnabled || !this.isLoaded()) {
|
if (!this._umap.editEnabled || !this.isLoaded()) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
const container = DomUtil.create('div', 'umap-layer-properties-container')
|
const container = DomUtil.create('div', 'umap-layer-properties-container')
|
||||||
|
@ -633,7 +635,7 @@ export class DataLayer extends ServerStored {
|
||||||
DomUtil.createTitle(container, translate('Layer properties'), 'icon-layers')
|
DomUtil.createTitle(container, translate('Layer properties'), 'icon-layers')
|
||||||
let builder = new U.FormBuilder(this, metadataFields, {
|
let builder = new U.FormBuilder(this, metadataFields, {
|
||||||
callback(e) {
|
callback(e) {
|
||||||
this.umap.onDataLayersChanged()
|
this._umap.onDataLayersChanged()
|
||||||
if (e.helper.field === 'options.type') {
|
if (e.helper.field === 'options.type') {
|
||||||
this.edit()
|
this.edit()
|
||||||
}
|
}
|
||||||
|
@ -744,7 +746,7 @@ export class DataLayer extends ServerStored {
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
]
|
]
|
||||||
if (this.umap.properties.urls.ajax_proxy) {
|
if (this._umap.properties.urls.ajax_proxy) {
|
||||||
remoteDataFields.push([
|
remoteDataFields.push([
|
||||||
'options.remoteData.proxy',
|
'options.remoteData.proxy',
|
||||||
{
|
{
|
||||||
|
@ -770,7 +772,7 @@ export class DataLayer extends ServerStored {
|
||||||
this
|
this
|
||||||
)
|
)
|
||||||
|
|
||||||
if (this.umap.properties.urls.datalayer_versions)
|
if (this._umap.properties.urls.datalayer_versions)
|
||||||
this.buildVersionsFieldset(container)
|
this.buildVersionsFieldset(container)
|
||||||
|
|
||||||
const advancedActions = DomUtil.createFieldset(
|
const advancedActions = DomUtil.createFieldset(
|
||||||
|
@ -784,7 +786,7 @@ export class DataLayer extends ServerStored {
|
||||||
</button>`)
|
</button>`)
|
||||||
deleteButton.addEventListener('click', () => {
|
deleteButton.addEventListener('click', () => {
|
||||||
this._delete()
|
this._delete()
|
||||||
this.umap.editPanel.close()
|
this._umap.editPanel.close()
|
||||||
})
|
})
|
||||||
advancedButtons.appendChild(deleteButton)
|
advancedButtons.appendChild(deleteButton)
|
||||||
|
|
||||||
|
@ -823,9 +825,9 @@ export class DataLayer extends ServerStored {
|
||||||
// Fixme: remove me when this is merged and released
|
// Fixme: remove me when this is merged and released
|
||||||
// https://github.com/Leaflet/Leaflet/pull/9052
|
// https://github.com/Leaflet/Leaflet/pull/9052
|
||||||
DomEvent.disableClickPropagation(backButton)
|
DomEvent.disableClickPropagation(backButton)
|
||||||
DomEvent.on(backButton, 'click', this.umap.editDatalayers, this.umap)
|
DomEvent.on(backButton, 'click', this._umap.editDatalayers, this._umap)
|
||||||
|
|
||||||
this.umap.editPanel.open({
|
this._umap.editPanel.open({
|
||||||
content: container,
|
content: container,
|
||||||
actions: [backButton],
|
actions: [backButton],
|
||||||
})
|
})
|
||||||
|
@ -846,7 +848,7 @@ export class DataLayer extends ServerStored {
|
||||||
if (this.layer?.defaults?.[option]) {
|
if (this.layer?.defaults?.[option]) {
|
||||||
return this.layer.defaults[option]
|
return this.layer.defaults[option]
|
||||||
}
|
}
|
||||||
return this.umap.getOption(option, feature)
|
return this._umap.getProperty(option, feature)
|
||||||
}
|
}
|
||||||
|
|
||||||
async buildVersionsFieldset(container) {
|
async buildVersionsFieldset(container) {
|
||||||
|
@ -867,7 +869,7 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
const versionsContainer = DomUtil.createFieldset(container, translate('Versions'), {
|
const versionsContainer = DomUtil.createFieldset(container, translate('Versions'), {
|
||||||
async callback() {
|
async callback() {
|
||||||
const [{ versions }, response, error] = await this.umap.server.get(
|
const [{ versions }, response, error] = await this._umap.server.get(
|
||||||
this.getVersionsUrl()
|
this.getVersionsUrl()
|
||||||
)
|
)
|
||||||
if (!error) versions.forEach(appendVersion)
|
if (!error) versions.forEach(appendVersion)
|
||||||
|
@ -877,11 +879,11 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
async restore(version) {
|
async restore(version) {
|
||||||
if (!this.umap.editEnabled) return
|
if (!this._umap.editEnabled) return
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.confirm(translate('Are you sure you want to restore this version?'))
|
.confirm(translate('Are you sure you want to restore this version?'))
|
||||||
.then(async () => {
|
.then(async () => {
|
||||||
const [geojson, response, error] = await this.umap.server.get(
|
const [geojson, response, error] = await this._umap.server.get(
|
||||||
this.getVersionUrl(version)
|
this.getVersionUrl(version)
|
||||||
)
|
)
|
||||||
if (!error) {
|
if (!error) {
|
||||||
|
@ -902,13 +904,13 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
async show() {
|
async show() {
|
||||||
this.umap._leafletMap.addLayer(this.layer)
|
this._leafletMap.addLayer(this.layer)
|
||||||
if (!this.isLoaded()) await this.fetchData()
|
if (!this.isLoaded()) await this.fetchData()
|
||||||
this.propagateShow()
|
this.propagateShow()
|
||||||
}
|
}
|
||||||
|
|
||||||
hide() {
|
hide() {
|
||||||
this.umap._leafletMap.removeLayer(this.layer)
|
this._leafletMap.removeLayer(this.layer)
|
||||||
this.propagateHide()
|
this.propagateHide()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -925,7 +927,7 @@ export class DataLayer extends ServerStored {
|
||||||
const bounds = this.layer.getBounds()
|
const bounds = this.layer.getBounds()
|
||||||
if (bounds.isValid()) {
|
if (bounds.isValid()) {
|
||||||
const options = { maxZoom: this.getOption('zoomTo') }
|
const options = { maxZoom: this.getOption('zoomTo') }
|
||||||
this.umap._leafletMap.fitBounds(bounds, options)
|
this._leafletMap.fitBounds(bounds, options)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -956,7 +958,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
isVisible() {
|
isVisible() {
|
||||||
return Boolean(this.layer && this.umap._leafletMap.hasLayer(this.layer))
|
return Boolean(this.layer && this._leafletMap.hasLayer(this.layer))
|
||||||
}
|
}
|
||||||
|
|
||||||
getFeatureByIndex(index) {
|
getFeatureByIndex(index) {
|
||||||
|
@ -993,7 +995,7 @@ export class DataLayer extends ServerStored {
|
||||||
getPreviousBrowsable() {
|
getPreviousBrowsable() {
|
||||||
let id = this.getRank()
|
let id = this.getRank()
|
||||||
let next
|
let next
|
||||||
const index = this.umap.datalayersIndex
|
const index = this._umap.datalayersIndex
|
||||||
while (((id = index[++id] ? id : 0), (next = index[id]))) {
|
while (((id = index[++id] ? id : 0), (next = index[id]))) {
|
||||||
if (next === this || next.canBrowse()) break
|
if (next === this || next.canBrowse()) break
|
||||||
}
|
}
|
||||||
|
@ -1003,7 +1005,7 @@ export class DataLayer extends ServerStored {
|
||||||
getNextBrowsable() {
|
getNextBrowsable() {
|
||||||
let id = this.getRank()
|
let id = this.getRank()
|
||||||
let prev
|
let prev
|
||||||
const index = this.umap.datalayersIndex
|
const index = this._umap.datalayersIndex
|
||||||
while (((id = index[--id] ? id : index.length - 1), (prev = index[id]))) {
|
while (((id = index[--id] ? id : index.length - 1), (prev = index[id]))) {
|
||||||
if (prev === this || prev.canBrowse()) break
|
if (prev === this || prev.canBrowse()) break
|
||||||
}
|
}
|
||||||
|
@ -1019,7 +1021,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
getRank() {
|
getRank() {
|
||||||
return this.umap.datalayersIndex.indexOf(this)
|
return this._umap.datalayersIndex.indexOf(this)
|
||||||
}
|
}
|
||||||
|
|
||||||
isReadOnly() {
|
isReadOnly() {
|
||||||
|
@ -1046,8 +1048,8 @@ export class DataLayer extends ServerStored {
|
||||||
// Filename support is shaky, don't do it for now.
|
// Filename support is shaky, don't do it for now.
|
||||||
const blob = new Blob([JSON.stringify(geojson)], { type: 'application/json' })
|
const blob = new Blob([JSON.stringify(geojson)], { type: 'application/json' })
|
||||||
formData.append('geojson', blob)
|
formData.append('geojson', blob)
|
||||||
const saveUrl = this.umap.urls.get('datalayer_save', {
|
const saveUrl = this._umap.urls.get('datalayer_save', {
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
pk: this.umap_id,
|
pk: this.umap_id,
|
||||||
})
|
})
|
||||||
const headers = this._reference_version
|
const headers = this._reference_version
|
||||||
|
@ -1059,7 +1061,7 @@ export class DataLayer extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
async _trySave(url, headers, formData) {
|
async _trySave(url, headers, formData) {
|
||||||
const [data, response, error] = await this.umap.server.post(url, headers, formData)
|
const [data, response, error] = await this._umap.server.post(url, headers, formData)
|
||||||
if (error) {
|
if (error) {
|
||||||
if (response && response.status === 412) {
|
if (response && response.status === 412) {
|
||||||
AlertConflict.error(
|
AlertConflict.error(
|
||||||
|
@ -1075,7 +1077,7 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
// Call the main save, in case something else needs to be saved
|
// Call the main save, in case something else needs to be saved
|
||||||
// as the conflict stopped the saving flow
|
// as the conflict stopped the saving flow
|
||||||
await this.umap.saveAll()
|
await this._umap.saveAll()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
@ -1104,23 +1106,19 @@ export class DataLayer extends ServerStored {
|
||||||
|
|
||||||
async saveDelete() {
|
async saveDelete() {
|
||||||
if (this.umap_id) {
|
if (this.umap_id) {
|
||||||
await this.umap.server.post(this.getDeleteUrl())
|
await this._umap.server.post(this.getDeleteUrl())
|
||||||
}
|
}
|
||||||
delete this.umap.datalayers[stamp(this)]
|
delete this._umap.datalayers[stamp(this)]
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
getMap() {
|
|
||||||
return this.map
|
|
||||||
}
|
|
||||||
|
|
||||||
getName() {
|
getName() {
|
||||||
return this.options.name || translate('Untitled layer')
|
return this.options.name || translate('Untitled layer')
|
||||||
}
|
}
|
||||||
|
|
||||||
tableEdit() {
|
tableEdit() {
|
||||||
if (!this.isVisible()) return
|
if (!this.isVisible()) return
|
||||||
const editor = new TableEditor(this)
|
const editor = new TableEditor(this._umap, this, this._leafletMap)
|
||||||
editor.open()
|
editor.open()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1128,9 +1126,9 @@ export class DataLayer extends ServerStored {
|
||||||
// This keys will be used to filter feature from the browser text input.
|
// This keys will be used to filter feature from the browser text input.
|
||||||
// By default, it will we use the "name" property, which is also the one used as label in the features list.
|
// By default, it will we use the "name" property, which is also the one used as label in the features list.
|
||||||
// When map owner has configured another label or sort key, we try to be smart and search in the same keys.
|
// When map owner has configured another label or sort key, we try to be smart and search in the same keys.
|
||||||
if (this.umap.properties.filterKey) return this.umap.properties.filterKey
|
if (this._umap.properties.filterKey) return this._umap.properties.filterKey
|
||||||
if (this.getOption('labelKey')) return this.getOption('labelKey')
|
if (this.getOption('labelKey')) return this.getOption('labelKey')
|
||||||
if (this.umap.properties.sortKey) return this.umap.properties.sortKey
|
if (this._umap.properties.sortKey) return this._umap.properties.sortKey
|
||||||
return 'displayName'
|
return 'displayName'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1181,7 +1179,7 @@ export class DataLayer extends ServerStored {
|
||||||
'click',
|
'click',
|
||||||
function () {
|
function () {
|
||||||
if (!this.isVisible()) return
|
if (!this.isVisible()) return
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.confirm(translate('Are you sure you want to delete this layer?'))
|
.confirm(translate('Are you sure you want to delete this layer?'))
|
||||||
.then(() => {
|
.then(() => {
|
||||||
this._delete()
|
this._delete()
|
||||||
|
|
|
@ -4,7 +4,7 @@ import * as Utils from './utils.js'
|
||||||
|
|
||||||
export default class Facets {
|
export default class Facets {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.selected = {}
|
this.selected = {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -24,7 +24,7 @@ export default class Facets {
|
||||||
this.selected[name] = selected
|
this.selected[name] = selected
|
||||||
}
|
}
|
||||||
|
|
||||||
this.umap.eachBrowsableDataLayer((datalayer) => {
|
this._umap.eachBrowsableDataLayer((datalayer) => {
|
||||||
datalayer.eachFeature((feature) => {
|
datalayer.eachFeature((feature) => {
|
||||||
for (const name of names) {
|
for (const name of names) {
|
||||||
let value = feature.properties[name]
|
let value = feature.properties[name]
|
||||||
|
@ -108,8 +108,8 @@ export default class Facets {
|
||||||
const defaultType = 'checkbox'
|
const defaultType = 'checkbox'
|
||||||
const allowedTypes = [defaultType, 'radio', 'number', 'date', 'datetime']
|
const allowedTypes = [defaultType, 'radio', 'number', 'date', 'datetime']
|
||||||
const defined = new Map()
|
const defined = new Map()
|
||||||
if (!this.umap.properties.facetKey) return defined
|
if (!this._umap.properties.facetKey) return defined
|
||||||
return (this.umap.properties.facetKey || '').split(',').reduce((acc, curr) => {
|
return (this._umap.properties.facetKey || '').split(',').reduce((acc, curr) => {
|
||||||
let [name, label, type] = curr.split('|')
|
let [name, label, type] = curr.split('|')
|
||||||
type = allowedTypes.includes(type) ? type : defaultType
|
type = allowedTypes.includes(type) ? type : defaultType
|
||||||
acc.set(name, { label: label || name, type: type })
|
acc.set(name, { label: label || name, type: type })
|
||||||
|
@ -146,15 +146,15 @@ export default class Facets {
|
||||||
const defined = this.getDefined()
|
const defined = this.getDefined()
|
||||||
if (!defined.has(property)) {
|
if (!defined.has(property)) {
|
||||||
defined.set(property, { label, type })
|
defined.set(property, { label, type })
|
||||||
this.umap.properties.facetKey = this.dumps(defined)
|
this._umap.properties.facetKey = this.dumps(defined)
|
||||||
this.umap.isDirty = true
|
this._umap.isDirty = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
remove(property) {
|
remove(property) {
|
||||||
const defined = this.getDefined()
|
const defined = this.getDefined()
|
||||||
defined.delete(property)
|
defined.delete(property)
|
||||||
this.umap.properties.facetKey = this.dumps(defined)
|
this._umap.properties.facetKey = this.dumps(defined)
|
||||||
this.umap.isDirty = true
|
this._umap.isDirty = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -49,7 +49,7 @@ const TEMPLATE = `
|
||||||
|
|
||||||
export default class Importer {
|
export default class Importer {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.TYPES = ['geojson', 'csv', 'gpx', 'kml', 'osm', 'georss', 'umap']
|
this.TYPES = ['geojson', 'csv', 'gpx', 'kml', 'osm', 'georss', 'umap']
|
||||||
this.IMPORTERS = []
|
this.IMPORTERS = []
|
||||||
this.loadImporters()
|
this.loadImporters()
|
||||||
|
@ -57,9 +57,9 @@ export default class Importer {
|
||||||
}
|
}
|
||||||
|
|
||||||
loadImporters() {
|
loadImporters() {
|
||||||
for (const [name, config] of Object.entries(this.umap.properties.importers || {})) {
|
for (const [name, config] of Object.entries(this._umap.properties.importers || {})) {
|
||||||
const register = (mod) => {
|
const register = (mod) => {
|
||||||
this.IMPORTERS.push(new mod.Importer(this.umap, config))
|
this.IMPORTERS.push(new mod.Importer(this._umap, config))
|
||||||
}
|
}
|
||||||
// We need to have explicit static paths for Django's collectstatic with hashes.
|
// We need to have explicit static paths for Django's collectstatic with hashes.
|
||||||
switch (name) {
|
switch (name) {
|
||||||
|
@ -139,8 +139,8 @@ export default class Importer {
|
||||||
|
|
||||||
get layer() {
|
get layer() {
|
||||||
return (
|
return (
|
||||||
this.umap.datalayers[this.layerId] ||
|
this._umap.datalayers[this.layerId] ||
|
||||||
this.umap.createDataLayer({ name: this.layerName })
|
this._umap.createDataLayer({ name: this.layerName })
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -167,7 +167,7 @@ export default class Importer {
|
||||||
textContent: type,
|
textContent: type,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
this.umap.help.parse(this.container)
|
this._umap.help.parse(this.container)
|
||||||
DomEvent.on(this.qs('[name=submit]'), 'click', this.submit, this)
|
DomEvent.on(this.qs('[name=submit]'), 'click', this.submit, this)
|
||||||
DomEvent.on(this.qs('[type=file]'), 'change', this.onFileChange, this)
|
DomEvent.on(this.qs('[type=file]'), 'change', this.onFileChange, this)
|
||||||
for (const element of this.container.querySelectorAll('[onchange]')) {
|
for (const element of this.container.querySelectorAll('[onchange]')) {
|
||||||
|
@ -206,7 +206,7 @@ export default class Importer {
|
||||||
this.layerName = null
|
this.layerName = null
|
||||||
const layerSelect = this.qs('[name="layer-id"]')
|
const layerSelect = this.qs('[name="layer-id"]')
|
||||||
layerSelect.innerHTML = ''
|
layerSelect.innerHTML = ''
|
||||||
this.umap.eachDataLayerReverse((datalayer) => {
|
this._umap.eachDataLayerReverse((datalayer) => {
|
||||||
if (datalayer.isLoaded() && !datalayer.isRemoteLayer()) {
|
if (datalayer.isLoaded() && !datalayer.isRemoteLayer()) {
|
||||||
DomUtil.element({
|
DomUtil.element({
|
||||||
tagName: 'option',
|
tagName: 'option',
|
||||||
|
@ -227,7 +227,7 @@ export default class Importer {
|
||||||
|
|
||||||
open() {
|
open() {
|
||||||
if (!this.container) this.build()
|
if (!this.container) this.build()
|
||||||
const onLoad = this.umap.editPanel.open({ content: this.container })
|
const onLoad = this._umap.editPanel.open({ content: this.container })
|
||||||
onLoad.then(() => this.onLoad())
|
onLoad.then(() => this.onLoad())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -254,12 +254,12 @@ export default class Importer {
|
||||||
try {
|
try {
|
||||||
if (this.files.length) {
|
if (this.files.length) {
|
||||||
for (const file of this.files) {
|
for (const file of this.files) {
|
||||||
this.umap.processFileToImport(file, null, 'umap')
|
this._umap.processFileToImport(file, null, 'umap')
|
||||||
}
|
}
|
||||||
} else if (this.raw) {
|
} else if (this.raw) {
|
||||||
this.umap.importRaw(this.raw)
|
this._umap.importRaw(this.raw)
|
||||||
} else if (this.url) {
|
} else if (this.url) {
|
||||||
this.umap.importFromUrl(this.url, this.format)
|
this._umap.importFromUrl(this.url, this.format)
|
||||||
}
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Alert.error(translate('Invalid umap data'))
|
Alert.error(translate('Invalid umap data'))
|
||||||
|
@ -281,7 +281,7 @@ export default class Importer {
|
||||||
url: this.url,
|
url: this.url,
|
||||||
format: this.format,
|
format: this.format,
|
||||||
}
|
}
|
||||||
if (this.umap.properties.urls.ajax_proxy) {
|
if (this._umap.properties.urls.ajax_proxy) {
|
||||||
layer.options.remoteData.proxy = true
|
layer.options.remoteData.proxy = true
|
||||||
layer.options.remoteData.ttl = SCHEMA.ttl.default
|
layer.options.remoteData.ttl = SCHEMA.ttl.default
|
||||||
}
|
}
|
||||||
|
@ -299,7 +299,7 @@ export default class Importer {
|
||||||
if (this.clear) layer.empty()
|
if (this.clear) layer.empty()
|
||||||
if (this.files.length) {
|
if (this.files.length) {
|
||||||
for (const file of this.files) {
|
for (const file of this.files) {
|
||||||
this.umap.processFileToImport(file, layer, this.format)
|
this._umap.processFileToImport(file, layer, this.format)
|
||||||
}
|
}
|
||||||
} else if (this.raw) {
|
} else if (this.raw) {
|
||||||
layer.importRaw(this.raw, this.format)
|
layer.importRaw(this.raw, this.format)
|
||||||
|
|
|
@ -9,13 +9,13 @@ import * as Utils from './utils.js'
|
||||||
export class MapPermissions extends ServerStored {
|
export class MapPermissions extends ServerStored {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
super()
|
super()
|
||||||
this.setOptions(umap.properties.permissions)
|
this.setProperties(umap.properties.permissions)
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this._isDirty = false
|
this._isDirty = false
|
||||||
}
|
}
|
||||||
|
|
||||||
setOptions(options) {
|
setProperties(properties) {
|
||||||
this.options = Object.assign(
|
this.properties = Object.assign(
|
||||||
{
|
{
|
||||||
owner: null,
|
owner: null,
|
||||||
team: null,
|
team: null,
|
||||||
|
@ -23,42 +23,42 @@ export class MapPermissions extends ServerStored {
|
||||||
share_status: null,
|
share_status: null,
|
||||||
edit_status: null,
|
edit_status: null,
|
||||||
},
|
},
|
||||||
options
|
properties
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
isOwner() {
|
isOwner() {
|
||||||
return Boolean(this.umap.properties.user?.is_owner)
|
return Boolean(this._umap.properties.user?.is_owner)
|
||||||
}
|
}
|
||||||
|
|
||||||
isAnonymousMap() {
|
isAnonymousMap() {
|
||||||
return !this.umap.properties.permissions.owner
|
return !this._umap.properties.permissions.owner
|
||||||
}
|
}
|
||||||
|
|
||||||
_editAnonymous(container) {
|
_editAnonymous(container) {
|
||||||
const fields = []
|
const fields = []
|
||||||
if (this.isOwner()) {
|
if (this.isOwner()) {
|
||||||
fields.push([
|
fields.push([
|
||||||
'options.edit_status',
|
'properties.edit_status',
|
||||||
{
|
{
|
||||||
handler: 'IntSelect',
|
handler: 'IntSelect',
|
||||||
label: translate('Who can edit'),
|
label: translate('Who can edit'),
|
||||||
selectOptions: this.umap.properties.edit_statuses,
|
selectOptions: this._umap.properties.edit_statuses,
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
const builder = new U.FormBuilder(this, fields)
|
const builder = new U.FormBuilder(this, fields)
|
||||||
const form = builder.build()
|
const form = builder.build()
|
||||||
container.appendChild(form)
|
container.appendChild(form)
|
||||||
|
|
||||||
if (this.options.anonymous_edit_url) {
|
if (this.properties.anonymous_edit_url) {
|
||||||
DomUtil.createCopiableInput(
|
DomUtil.createCopiableInput(
|
||||||
container,
|
container,
|
||||||
translate('Secret edit link:'),
|
translate('Secret edit link:'),
|
||||||
this.options.anonymous_edit_url
|
this.properties.anonymous_edit_url
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.umap.properties.user?.id) {
|
if (this._umap.properties.user?.id) {
|
||||||
// We have a user, and this user has come through here, so they can edit the map, so let's allow to own the map.
|
// We have a user, and this user has come through here, so they can edit the map, so let's allow to own the map.
|
||||||
// Note: real check is made on the back office anyway.
|
// Note: real check is made on the back office anyway.
|
||||||
const advancedActions = DomUtil.createFieldset(
|
const advancedActions = DomUtil.createFieldset(
|
||||||
|
@ -86,38 +86,38 @@ export class MapPermissions extends ServerStored {
|
||||||
container.appendChild(fieldset)
|
container.appendChild(fieldset)
|
||||||
if (this.isOwner()) {
|
if (this.isOwner()) {
|
||||||
topFields.push([
|
topFields.push([
|
||||||
'options.edit_status',
|
'properties.edit_status',
|
||||||
{
|
{
|
||||||
handler: 'IntSelect',
|
handler: 'IntSelect',
|
||||||
label: translate('Who can edit'),
|
label: translate('Who can edit'),
|
||||||
selectOptions: this.umap.properties.edit_statuses,
|
selectOptions: this._umap.properties.edit_statuses,
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
topFields.push([
|
topFields.push([
|
||||||
'options.share_status',
|
'properties.share_status',
|
||||||
{
|
{
|
||||||
handler: 'IntSelect',
|
handler: 'IntSelect',
|
||||||
label: translate('Who can view'),
|
label: translate('Who can view'),
|
||||||
selectOptions: this.umap.properties.share_statuses,
|
selectOptions: this._umap.properties.share_statuses,
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
collaboratorsFields.push([
|
collaboratorsFields.push([
|
||||||
'options.owner',
|
'properties.owner',
|
||||||
{ handler: 'ManageOwner', label: translate("Map's owner") },
|
{ handler: 'ManageOwner', label: translate("Map's owner") },
|
||||||
])
|
])
|
||||||
if (this.umap.properties.user?.teams?.length) {
|
if (this._umap.properties.user?.teams?.length) {
|
||||||
collaboratorsFields.push([
|
collaboratorsFields.push([
|
||||||
'options.team',
|
'properties.team',
|
||||||
{
|
{
|
||||||
handler: 'ManageTeam',
|
handler: 'ManageTeam',
|
||||||
label: translate('Attach map to a team'),
|
label: translate('Attach map to a team'),
|
||||||
teams: this.umap.properties.user.teams,
|
teams: this._umap.properties.user.teams,
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
collaboratorsFields.push([
|
collaboratorsFields.push([
|
||||||
'options.editors',
|
'properties.editors',
|
||||||
{ handler: 'ManageEditors', label: translate("Map's editors") },
|
{ handler: 'ManageEditors', label: translate("Map's editors") },
|
||||||
])
|
])
|
||||||
|
|
||||||
|
@ -136,20 +136,20 @@ export class MapPermissions extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
_editDatalayers(container) {
|
_editDatalayers(container) {
|
||||||
if (this.umap.hasLayers()) {
|
if (this._umap.hasLayers()) {
|
||||||
const fieldset = Utils.loadTemplate(
|
const fieldset = Utils.loadTemplate(
|
||||||
`<fieldset class="separator"><legend>${translate('Datalayers')}</legend></fieldset>`
|
`<fieldset class="separator"><legend>${translate('Datalayers')}</legend></fieldset>`
|
||||||
)
|
)
|
||||||
container.appendChild(fieldset)
|
container.appendChild(fieldset)
|
||||||
this.umap.eachDataLayer((datalayer) => {
|
this._umap.eachDataLayer((datalayer) => {
|
||||||
datalayer.permissions.edit(fieldset)
|
datalayer.permissions.edit(fieldset)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
edit() {
|
edit() {
|
||||||
if (this.umap.properties.editMode !== 'advanced') return
|
if (this._umap.properties.editMode !== 'advanced') return
|
||||||
if (!this.umap.properties.umap_id) {
|
if (!this._umap.properties.umap_id) {
|
||||||
Alert.info(translate('Please save the map first'))
|
Alert.info(translate('Please save the map first'))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -158,35 +158,35 @@ export class MapPermissions extends ServerStored {
|
||||||
if (this.isAnonymousMap()) this._editAnonymous(container)
|
if (this.isAnonymousMap()) this._editAnonymous(container)
|
||||||
else this._editWithOwner(container)
|
else this._editWithOwner(container)
|
||||||
this._editDatalayers(container)
|
this._editDatalayers(container)
|
||||||
this.umap.editPanel.open({ content: container, className: 'dark' })
|
this._umap.editPanel.open({ content: container, className: 'dark' })
|
||||||
}
|
}
|
||||||
|
|
||||||
async attach() {
|
async attach() {
|
||||||
const [data, response, error] = await this.umap.server.post(this.getAttachUrl())
|
const [data, response, error] = await this._umap.server.post(this.getAttachUrl())
|
||||||
if (!error) {
|
if (!error) {
|
||||||
this.options.owner = this.umap.properties.user
|
this.properties.owner = this._umap.properties.user
|
||||||
Alert.success(translate('Map has been attached to your account'))
|
Alert.success(translate('Map has been attached to your account'))
|
||||||
this.umap.editPanel.close()
|
this._umap.editPanel.close()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async save() {
|
async save() {
|
||||||
if (!this.isDirty) return
|
if (!this.isDirty) return
|
||||||
const formData = new FormData()
|
const formData = new FormData()
|
||||||
if (!this.isAnonymousMap() && this.options.editors) {
|
if (!this.isAnonymousMap() && this.properties.editors) {
|
||||||
const editors = this.options.editors.map((u) => u.id)
|
const editors = this.properties.editors.map((u) => u.id)
|
||||||
for (let i = 0; i < this.options.editors.length; i++)
|
for (let i = 0; i < this.properties.editors.length; i++)
|
||||||
formData.append('editors', this.options.editors[i].id)
|
formData.append('editors', this.properties.editors[i].id)
|
||||||
}
|
}
|
||||||
if (this.isOwner() || this.isAnonymousMap()) {
|
if (this.isOwner() || this.isAnonymousMap()) {
|
||||||
formData.append('edit_status', this.options.edit_status)
|
formData.append('edit_status', this.properties.edit_status)
|
||||||
}
|
}
|
||||||
if (this.isOwner()) {
|
if (this.isOwner()) {
|
||||||
formData.append('owner', this.options.owner?.id)
|
formData.append('owner', this.properties.owner?.id)
|
||||||
formData.append('team', this.options.team?.id || '')
|
formData.append('team', this.properties.team?.id || '')
|
||||||
formData.append('share_status', this.options.share_status)
|
formData.append('share_status', this.properties.share_status)
|
||||||
}
|
}
|
||||||
const [data, response, error] = await this.umap.server.post(
|
const [data, response, error] = await this._umap.server.post(
|
||||||
this.getUrl(),
|
this.getUrl(),
|
||||||
{},
|
{},
|
||||||
formData
|
formData
|
||||||
|
@ -198,38 +198,39 @@ export class MapPermissions extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
getUrl() {
|
getUrl() {
|
||||||
return this.umap.urls.get('map_update_permissions', {
|
return this._umap.urls.get('map_update_permissions', {
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
getAttachUrl() {
|
getAttachUrl() {
|
||||||
return this.umap.urls.get('map_attach_owner', {
|
return this._umap.urls.get('map_attach_owner', {
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
commit() {
|
commit() {
|
||||||
this.umap.properties.permissions = Object.assign(
|
this._umap.properties.permissions = Object.assign(
|
||||||
{},
|
{},
|
||||||
this.umap.properties.permissions,
|
this._umap.properties.permissions,
|
||||||
this.options
|
this.properties
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
getShareStatusDisplay() {
|
getShareStatusDisplay() {
|
||||||
if (this.umap.properties.share_statuses) {
|
if (this._umap.properties.share_statuses) {
|
||||||
return Object.fromEntries(this.umap.properties.share_statuses)[
|
return Object.fromEntries(this._umap.properties.share_statuses)[
|
||||||
this.options.share_status
|
this.properties.share_status
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class DataLayerPermissions extends ServerStored {
|
export class DataLayerPermissions extends ServerStored {
|
||||||
constructor(datalayer) {
|
constructor(umap, datalayer) {
|
||||||
super()
|
super()
|
||||||
this.options = Object.assign(
|
this._umap = umap
|
||||||
|
this.properties = Object.assign(
|
||||||
{
|
{
|
||||||
edit_status: null,
|
edit_status: null,
|
||||||
},
|
},
|
||||||
|
@ -239,20 +240,16 @@ export class DataLayerPermissions extends ServerStored {
|
||||||
this.datalayer = datalayer
|
this.datalayer = datalayer
|
||||||
}
|
}
|
||||||
|
|
||||||
get umap() {
|
|
||||||
return this.datalayer.umap
|
|
||||||
}
|
|
||||||
|
|
||||||
edit(container) {
|
edit(container) {
|
||||||
const fields = [
|
const fields = [
|
||||||
[
|
[
|
||||||
'options.edit_status',
|
'properties.edit_status',
|
||||||
{
|
{
|
||||||
handler: 'IntSelect',
|
handler: 'IntSelect',
|
||||||
label: translate('Who can edit "{layer}"', {
|
label: translate('Who can edit "{layer}"', {
|
||||||
layer: this.datalayer.getName(),
|
layer: this.datalayer.getName(),
|
||||||
}),
|
}),
|
||||||
selectOptions: this.umap.properties.datalayer_edit_statuses,
|
selectOptions: this._umap.properties.datalayer_edit_statuses,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
]
|
]
|
||||||
|
@ -264,8 +261,8 @@ export class DataLayerPermissions extends ServerStored {
|
||||||
}
|
}
|
||||||
|
|
||||||
getUrl() {
|
getUrl() {
|
||||||
return this.umap.urls.get('datalayer_permissions', {
|
return this._umap.urls.get('datalayer_permissions', {
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
pk: this.datalayer.umap_id,
|
pk: this.datalayer.umap_id,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -273,8 +270,8 @@ export class DataLayerPermissions extends ServerStored {
|
||||||
async save() {
|
async save() {
|
||||||
if (!this.isDirty) return
|
if (!this.isDirty) return
|
||||||
const formData = new FormData()
|
const formData = new FormData()
|
||||||
formData.append('edit_status', this.options.edit_status)
|
formData.append('edit_status', this.properties.edit_status)
|
||||||
const [data, response, error] = await this.umap.server.post(
|
const [data, response, error] = await this._umap.server.post(
|
||||||
this.getUrl(),
|
this.getUrl(),
|
||||||
{},
|
{},
|
||||||
formData
|
formData
|
||||||
|
@ -289,7 +286,7 @@ export class DataLayerPermissions extends ServerStored {
|
||||||
this.datalayer.options.permissions = Object.assign(
|
this.datalayer.options.permissions = Object.assign(
|
||||||
{},
|
{},
|
||||||
this.datalayer.options.permissions,
|
this.datalayer.options.permissions,
|
||||||
this.options
|
this.properties
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,20 +5,20 @@ import * as Utils from '../../utils.js'
|
||||||
export const LayerMixin = {
|
export const LayerMixin = {
|
||||||
browsable: true,
|
browsable: true,
|
||||||
|
|
||||||
onInit: function (map) {
|
onInit: function (leafletMap) {
|
||||||
if (this.datalayer.autoLoaded()) map.on('zoomend', this.onZoomEnd, this)
|
if (this.datalayer.autoLoaded()) leafletMap.on('zoomend', this.onZoomEnd, this)
|
||||||
},
|
},
|
||||||
|
|
||||||
onDelete: function (map) {
|
onDelete: function (leafletMap) {
|
||||||
map.off('zoomend', this.onZoomEnd, this)
|
leafletMap.off('zoomend', this.onZoomEnd, this)
|
||||||
},
|
},
|
||||||
|
|
||||||
onAdd: function (map) {
|
onAdd: function (leafletMap) {
|
||||||
map.on('moveend', this.onMoveEnd, this)
|
leafletMap.on('moveend', this.onMoveEnd, this)
|
||||||
},
|
},
|
||||||
|
|
||||||
onRemove: function (map) {
|
onRemove: function (leafletMap) {
|
||||||
map.off('moveend', this.onMoveEnd, this)
|
leafletMap.off('moveend', this.onMoveEnd, this)
|
||||||
},
|
},
|
||||||
|
|
||||||
getType: function () {
|
getType: function () {
|
||||||
|
@ -73,17 +73,17 @@ export const Default = FeatureGroup.extend({
|
||||||
initialize: function (datalayer) {
|
initialize: function (datalayer) {
|
||||||
this.datalayer = datalayer
|
this.datalayer = datalayer
|
||||||
FeatureGroup.prototype.initialize.call(this)
|
FeatureGroup.prototype.initialize.call(this)
|
||||||
LayerMixin.onInit.call(this, this.datalayer.umap._leafletMap)
|
LayerMixin.onInit.call(this, this.datalayer._leafletMap)
|
||||||
},
|
},
|
||||||
|
|
||||||
onAdd: function (map) {
|
onAdd: function (leafletMap) {
|
||||||
LayerMixin.onAdd.call(this, map)
|
LayerMixin.onAdd.call(this, leafletMap)
|
||||||
return FeatureGroup.prototype.onAdd.call(this, map)
|
return FeatureGroup.prototype.onAdd.call(this, leafletMap)
|
||||||
},
|
},
|
||||||
|
|
||||||
onRemove: function (map) {
|
onRemove: function (leafletMap) {
|
||||||
LayerMixin.onRemove.call(this, map)
|
LayerMixin.onRemove.call(this, leafletMap)
|
||||||
return FeatureGroup.prototype.onRemove.call(this, map)
|
return FeatureGroup.prototype.onRemove.call(this, leafletMap)
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
|
@ -20,7 +20,7 @@ const ClassifiedMixin = {
|
||||||
}
|
}
|
||||||
this.ensureOptions(this.datalayer.options[key])
|
this.ensureOptions(this.datalayer.options[key])
|
||||||
FeatureGroup.prototype.initialize.call(this, [], this.datalayer.options[key])
|
FeatureGroup.prototype.initialize.call(this, [], this.datalayer.options[key])
|
||||||
LayerMixin.onInit.call(this, this.datalayer.umap._leafletMap)
|
LayerMixin.onInit.call(this, this.datalayer._leafletMap)
|
||||||
},
|
},
|
||||||
|
|
||||||
ensureOptions: () => {},
|
ensureOptions: () => {},
|
||||||
|
|
|
@ -40,7 +40,7 @@ export const Cluster = L.MarkerClusterGroup.extend({
|
||||||
options.maxClusterRadius = this.datalayer.options.cluster.radius
|
options.maxClusterRadius = this.datalayer.options.cluster.radius
|
||||||
}
|
}
|
||||||
L.MarkerClusterGroup.prototype.initialize.call(this, options)
|
L.MarkerClusterGroup.prototype.initialize.call(this, options)
|
||||||
LayerMixin.onInit.call(this, this.datalayer.umap._leafletMap)
|
LayerMixin.onInit.call(this, this.datalayer._leafletMap)
|
||||||
this._markerCluster = MarkerCluster
|
this._markerCluster = MarkerCluster
|
||||||
this._layers = []
|
this._layers = []
|
||||||
},
|
},
|
||||||
|
|
|
@ -21,7 +21,7 @@ export const Heat = L.HeatLayer.extend({
|
||||||
initialize: function (datalayer) {
|
initialize: function (datalayer) {
|
||||||
this.datalayer = datalayer
|
this.datalayer = datalayer
|
||||||
L.HeatLayer.prototype.initialize.call(this, [], this.datalayer.options.heat)
|
L.HeatLayer.prototype.initialize.call(this, [], this.datalayer.options.heat)
|
||||||
LayerMixin.onInit.call(this, this.datalayer.umap._leafletMap)
|
LayerMixin.onInit.call(this, this.datalayer._leafletMap)
|
||||||
if (!Utils.isObject(this.datalayer.options.heat)) {
|
if (!Utils.isObject(this.datalayer.options.heat)) {
|
||||||
this.datalayer.options.heat = {}
|
this.datalayer.options.heat = {}
|
||||||
}
|
}
|
||||||
|
|
|
@ -39,7 +39,7 @@ const ControlsMixin = {
|
||||||
initControls: function () {
|
initControls: function () {
|
||||||
this._controls = {}
|
this._controls = {}
|
||||||
|
|
||||||
if (this.umap.hasEditMode() && !this.options.noControl) {
|
if (this._umap.hasEditMode() && !this.options.noControl) {
|
||||||
new U.EditControl(this).addTo(this)
|
new U.EditControl(this).addTo(this)
|
||||||
|
|
||||||
new U.DrawToolbar({ map: this }).addTo(this)
|
new U.DrawToolbar({ map: this }).addTo(this)
|
||||||
|
@ -60,8 +60,8 @@ const ControlsMixin = {
|
||||||
zoomInTitle: translate('Zoom in'),
|
zoomInTitle: translate('Zoom in'),
|
||||||
zoomOutTitle: translate('Zoom out'),
|
zoomOutTitle: translate('Zoom out'),
|
||||||
})
|
})
|
||||||
this._controls.datalayers = new U.DataLayersControl(this.umap)
|
this._controls.datalayers = new U.DataLayersControl(this._umap)
|
||||||
this._controls.caption = new U.CaptionControl(this.umap)
|
this._controls.caption = new U.CaptionControl(this._umap)
|
||||||
this._controls.locate = new U.Locate(this, {
|
this._controls.locate = new U.Locate(this, {
|
||||||
strings: {
|
strings: {
|
||||||
title: translate('Center map on your location'),
|
title: translate('Center map on your location'),
|
||||||
|
@ -82,9 +82,9 @@ const ControlsMixin = {
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
this._controls.search = new U.SearchControl()
|
this._controls.search = new U.SearchControl()
|
||||||
this._controls.embed = new Control.Embed(this.umap)
|
this._controls.embed = new Control.Embed(this._umap)
|
||||||
this._controls.tilelayersChooser = new U.TileLayerChooser(this)
|
this._controls.tilelayersChooser = new U.TileLayerChooser(this)
|
||||||
if (this.options.user?.id) this._controls.star = new U.StarControl(this.umap)
|
if (this.options.user?.id) this._controls.star = new U.StarControl(this._umap)
|
||||||
this._controls.editinosm = new Control.EditInOSM({
|
this._controls.editinosm = new Control.EditInOSM({
|
||||||
position: 'topleft',
|
position: 'topleft',
|
||||||
widgetOptions: {
|
widgetOptions: {
|
||||||
|
@ -99,7 +99,7 @@ const ControlsMixin = {
|
||||||
this._controls.permanentCredit = new U.PermanentCreditsControl(this)
|
this._controls.permanentCredit = new U.PermanentCreditsControl(this)
|
||||||
if (this.options.scrollWheelZoom) this.scrollWheelZoom.enable()
|
if (this.options.scrollWheelZoom) this.scrollWheelZoom.enable()
|
||||||
else this.scrollWheelZoom.disable()
|
else this.scrollWheelZoom.disable()
|
||||||
this.umap.drop = new U.DropControl(this)
|
this._umap.drop = new U.DropControl(this)
|
||||||
this._controls.tilelayers = new U.TileLayerControl(this)
|
this._controls.tilelayers = new U.TileLayerControl(this)
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -119,13 +119,13 @@ const ControlsMixin = {
|
||||||
if (this.selectedTilelayer) {
|
if (this.selectedTilelayer) {
|
||||||
this._controls.miniMap = new Control.MiniMap(this.selectedTilelayer, {
|
this._controls.miniMap = new Control.MiniMap(this.selectedTilelayer, {
|
||||||
aimingRectOptions: {
|
aimingRectOptions: {
|
||||||
color: this.umap.getOption('color'),
|
color: this._umap.getProperty('color'),
|
||||||
fillColor: this.umap.getOption('fillColor'),
|
fillColor: this._umap.getProperty('fillColor'),
|
||||||
stroke: this.umap.getOption('stroke'),
|
stroke: this._umap.getProperty('stroke'),
|
||||||
fill: this.umap.getOption('fill'),
|
fill: this._umap.getProperty('fill'),
|
||||||
weight: this.umap.getOption('weight'),
|
weight: this._umap.getProperty('weight'),
|
||||||
opacity: this.umap.getOption('opacity'),
|
opacity: this._umap.getProperty('opacity'),
|
||||||
fillOpacity: this.umap.getOption('fillOpacity'),
|
fillOpacity: this._umap.getProperty('fillOpacity'),
|
||||||
},
|
},
|
||||||
}).addTo(this)
|
}).addTo(this)
|
||||||
this._controls.miniMap._miniMap.invalidateSize()
|
this._controls.miniMap._miniMap.invalidateSize()
|
||||||
|
@ -133,7 +133,7 @@ const ControlsMixin = {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
for (const name of this.HIDDABLE_CONTROLS) {
|
for (const name of this.HIDDABLE_CONTROLS) {
|
||||||
const status = this.umap.getOption(`${name}Control`)
|
const status = this._umap.getProperty(`${name}Control`)
|
||||||
if (status === false) continue
|
if (status === false) continue
|
||||||
const control = this._controls[name]
|
const control = this._controls[name]
|
||||||
if (!control) continue
|
if (!control) continue
|
||||||
|
@ -144,10 +144,10 @@ const ControlsMixin = {
|
||||||
DomUtil.removeClass(control._container, 'display-on-more')
|
DomUtil.removeClass(control._container, 'display-on-more')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (this.umap.getOption('permanentCredit'))
|
if (this._umap.getProperty('permanentCredit'))
|
||||||
this._controls.permanentCredit.addTo(this)
|
this._controls.permanentCredit.addTo(this)
|
||||||
if (this.umap.getOption('moreControl')) this._controls.more.addTo(this)
|
if (this._umap.getProperty('moreControl')) this._controls.more.addTo(this)
|
||||||
if (this.umap.getOption('scaleControl')) this._controls.scale.addTo(this)
|
if (this._umap.getProperty('scaleControl')) this._controls.scale.addTo(this)
|
||||||
this._controls.tilelayers.setLayers()
|
this._controls.tilelayers.setLayers()
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -163,7 +163,7 @@ const ControlsMixin = {
|
||||||
DomUtil.createLink('', logo, 'uMap', '/', null, translate('Go to the homepage'))
|
DomUtil.createLink('', logo, 'uMap', '/', null, translate('Go to the homepage'))
|
||||||
const nameButton = DomUtil.createButton('map-name', leftContainer, '')
|
const nameButton = DomUtil.createButton('map-name', leftContainer, '')
|
||||||
DomEvent.on(nameButton, 'mouseover', () => {
|
DomEvent.on(nameButton, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: translate('Edit the title of the map'),
|
content: translate('Edit the title of the map'),
|
||||||
anchor: nameButton,
|
anchor: nameButton,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
|
@ -175,11 +175,11 @@ const ControlsMixin = {
|
||||||
'share-status',
|
'share-status',
|
||||||
leftContainer,
|
leftContainer,
|
||||||
'',
|
'',
|
||||||
this.umap.permissions.edit,
|
this._umap.permissions.edit,
|
||||||
this.umap.permissions
|
this._umap.permissions
|
||||||
)
|
)
|
||||||
DomEvent.on(shareStatusButton, 'mouseover', () => {
|
DomEvent.on(shareStatusButton, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: translate('Update who can see and edit the map'),
|
content: translate('Update who can see and edit the map'),
|
||||||
anchor: shareStatusButton,
|
anchor: shareStatusButton,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
|
@ -188,12 +188,12 @@ const ControlsMixin = {
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
if (this.options.editMode === 'advanced') {
|
if (this.options.editMode === 'advanced') {
|
||||||
DomEvent.on(nameButton, 'click', this.umap.editCaption, this.umap)
|
DomEvent.on(nameButton, 'click', this._umap.editCaption, this._umap)
|
||||||
DomEvent.on(
|
DomEvent.on(
|
||||||
shareStatusButton,
|
shareStatusButton,
|
||||||
'click',
|
'click',
|
||||||
this.umap.permissions.edit,
|
this._umap.permissions.edit,
|
||||||
this.umap.permissions
|
this._umap.permissions
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
if (this.options.user?.id) {
|
if (this.options.user?.id) {
|
||||||
|
@ -208,21 +208,21 @@ const ControlsMixin = {
|
||||||
const actions = [
|
const actions = [
|
||||||
{
|
{
|
||||||
label: translate('New map'),
|
label: translate('New map'),
|
||||||
action: this.umap.urls.get('map_new'),
|
action: this._umap.urls.get('map_new'),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: translate('My maps'),
|
label: translate('My maps'),
|
||||||
action: this.umap.urls.get('user_dashboard'),
|
action: this._umap.urls.get('user_dashboard'),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: translate('My teams'),
|
label: translate('My teams'),
|
||||||
action: this.umap.urls.get('user_teams'),
|
action: this._umap.urls.get('user_teams'),
|
||||||
},
|
},
|
||||||
]
|
]
|
||||||
if (this.umap.urls.has('user_profile')) {
|
if (this._umap.urls.has('user_profile')) {
|
||||||
actions.push({
|
actions.push({
|
||||||
label: translate('My profile'),
|
label: translate('My profile'),
|
||||||
action: this.umap.urls.get('user_profile'),
|
action: this._umap.urls.get('user_profile'),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
button.addEventListener('click', () => {
|
button.addEventListener('click', () => {
|
||||||
|
@ -230,7 +230,7 @@ const ControlsMixin = {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
const connectedPeers = this.umap.sync.getNumberOfConnectedPeers()
|
const connectedPeers = this._umap.sync.getNumberOfConnectedPeers()
|
||||||
if (connectedPeers !== 0) {
|
if (connectedPeers !== 0) {
|
||||||
const connectedPeersCount = DomUtil.createButton(
|
const connectedPeersCount = DomUtil.createButton(
|
||||||
'leaflet-control-connected-peers',
|
'leaflet-control-connected-peers',
|
||||||
|
@ -238,7 +238,7 @@ const ControlsMixin = {
|
||||||
''
|
''
|
||||||
)
|
)
|
||||||
DomEvent.on(connectedPeersCount, 'mouseover', () => {
|
DomEvent.on(connectedPeersCount, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: translate(
|
content: translate(
|
||||||
'{connectedPeers} peer(s) currently connected to this map',
|
'{connectedPeers} peer(s) currently connected to this map',
|
||||||
{
|
{
|
||||||
|
@ -253,21 +253,21 @@ const ControlsMixin = {
|
||||||
})
|
})
|
||||||
|
|
||||||
const updateConnectedPeersCount = () => {
|
const updateConnectedPeersCount = () => {
|
||||||
connectedPeersCount.innerHTML = this.umap.sync.getNumberOfConnectedPeers()
|
connectedPeersCount.innerHTML = this._umap.sync.getNumberOfConnectedPeers()
|
||||||
}
|
}
|
||||||
updateConnectedPeersCount()
|
updateConnectedPeersCount()
|
||||||
}
|
}
|
||||||
|
|
||||||
this.umap.help.getStartedLink(rightContainer)
|
this._umap.help.getStartedLink(rightContainer)
|
||||||
const controlEditCancel = DomUtil.createButton(
|
const controlEditCancel = DomUtil.createButton(
|
||||||
'leaflet-control-edit-cancel',
|
'leaflet-control-edit-cancel',
|
||||||
rightContainer,
|
rightContainer,
|
||||||
DomUtil.add('span', '', null, translate('Cancel edits')),
|
DomUtil.add('span', '', null, translate('Cancel edits')),
|
||||||
() => this.umap.askForReset()
|
() => this._umap.askForReset()
|
||||||
)
|
)
|
||||||
DomEvent.on(controlEditCancel, 'mouseover', () => {
|
DomEvent.on(controlEditCancel, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: this.umap.help.displayLabel('CANCEL'),
|
content: this._umap.help.displayLabel('CANCEL'),
|
||||||
anchor: controlEditCancel,
|
anchor: controlEditCancel,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
delay: 500,
|
delay: 500,
|
||||||
|
@ -278,12 +278,12 @@ const ControlsMixin = {
|
||||||
'leaflet-control-edit-disable',
|
'leaflet-control-edit-disable',
|
||||||
rightContainer,
|
rightContainer,
|
||||||
DomUtil.add('span', '', null, translate('View')),
|
DomUtil.add('span', '', null, translate('View')),
|
||||||
this.umap.disableEdit,
|
this._umap.disableEdit,
|
||||||
this.umap
|
this._umap
|
||||||
)
|
)
|
||||||
DomEvent.on(controlEditDisable, 'mouseover', () => {
|
DomEvent.on(controlEditDisable, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: this.umap.help.displayLabel('PREVIEW'),
|
content: this._umap.help.displayLabel('PREVIEW'),
|
||||||
anchor: controlEditDisable,
|
anchor: controlEditDisable,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
delay: 500,
|
delay: 500,
|
||||||
|
@ -294,11 +294,11 @@ const ControlsMixin = {
|
||||||
'leaflet-control-edit-save button',
|
'leaflet-control-edit-save button',
|
||||||
rightContainer,
|
rightContainer,
|
||||||
DomUtil.add('span', '', null, translate('Save')),
|
DomUtil.add('span', '', null, translate('Save')),
|
||||||
() => this.umap.saveAll()
|
() => this._umap.saveAll()
|
||||||
)
|
)
|
||||||
DomEvent.on(controlEditSave, 'mouseover', () => {
|
DomEvent.on(controlEditSave, 'mouseover', () => {
|
||||||
this.umap.tooltip.open({
|
this._umap.tooltip.open({
|
||||||
content: this.umap.help.displayLabel('SAVE'),
|
content: this._umap.help.displayLabel('SAVE'),
|
||||||
anchor: controlEditSave,
|
anchor: controlEditSave,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
delay: 500,
|
delay: 500,
|
||||||
|
@ -315,13 +315,13 @@ const ControlsMixin = {
|
||||||
container.innerHTML = ''
|
container.innerHTML = ''
|
||||||
const name = DomUtil.create('h3', 'map-name', container)
|
const name = DomUtil.create('h3', 'map-name', container)
|
||||||
DomEvent.disableClickPropagation(container)
|
DomEvent.disableClickPropagation(container)
|
||||||
this.umap.addAuthorLink(container)
|
this._umap.addAuthorLink(container)
|
||||||
if (this.umap.getOption('captionMenus')) {
|
if (this._umap.getProperty('captionMenus')) {
|
||||||
DomUtil.createButton(
|
DomUtil.createButton(
|
||||||
'umap-about-link flat',
|
'umap-about-link flat',
|
||||||
container,
|
container,
|
||||||
translate('Open caption'),
|
translate('Open caption'),
|
||||||
() => this.umap.openCaption()
|
() => this._umap.openCaption()
|
||||||
)
|
)
|
||||||
DomUtil.createButton(
|
DomUtil.createButton(
|
||||||
'umap-open-browser-link flat',
|
'umap-open-browser-link flat',
|
||||||
|
@ -338,8 +338,8 @@ const ControlsMixin = {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
this.umap.onceDatalayersLoaded(() => {
|
this._umap.onceDatalayersLoaded(() => {
|
||||||
this.umap.slideshow.renderToolbox(container)
|
this._umap.slideshow.renderToolbox(container)
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@ -434,7 +434,7 @@ const ManageTilelayerMixin = {
|
||||||
updateTileLayers: function () {
|
updateTileLayers: function () {
|
||||||
const callback = (tilelayer) => {
|
const callback = (tilelayer) => {
|
||||||
this.options.tilelayer = tilelayer.toJSON()
|
this.options.tilelayer = tilelayer.toJSON()
|
||||||
this.umap.isDirty = true
|
this._umap.isDirty = true
|
||||||
}
|
}
|
||||||
if (this._controls.tilelayersChooser) {
|
if (this._controls.tilelayersChooser) {
|
||||||
this._controls.tilelayersChooser.openSwitcher({ callback, edit: true })
|
this._controls.tilelayersChooser.openSwitcher({ callback, edit: true })
|
||||||
|
@ -442,30 +442,17 @@ const ManageTilelayerMixin = {
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
const EditMixin = {
|
|
||||||
startMarker: function () {
|
|
||||||
return this.editTools.startMarker()
|
|
||||||
},
|
|
||||||
|
|
||||||
startPolyline: function () {
|
|
||||||
return this.editTools.startPolyline()
|
|
||||||
},
|
|
||||||
|
|
||||||
startPolygon: function () {
|
|
||||||
return this.editTools.startPolygon()
|
|
||||||
},
|
|
||||||
|
|
||||||
initEditTools: function () {
|
|
||||||
this.editTools = new U.Editable(this.umap)
|
|
||||||
this.renderEditToolbar()
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
export const LeafletMap = BaseMap.extend({
|
export const LeafletMap = BaseMap.extend({
|
||||||
includes: [ControlsMixin, ManageTilelayerMixin, EditMixin],
|
includes: [ControlsMixin, ManageTilelayerMixin],
|
||||||
|
|
||||||
|
// The initialize and the setup method might seem similar, but they
|
||||||
|
// serve two different purposes:
|
||||||
|
// initialize is for Leaflet internal, when we do "new LeafletMap",
|
||||||
|
// while setup is the public API for the LeafletMap to actually
|
||||||
|
// render to the DOM.
|
||||||
initialize: function (umap, element) {
|
initialize: function (umap, element) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
const options = this.umap.properties
|
const options = this._umap.properties
|
||||||
|
|
||||||
BaseMap.prototype.initialize.call(this, element, options)
|
BaseMap.prototype.initialize.call(this, element, options)
|
||||||
|
|
||||||
|
@ -489,11 +476,11 @@ export const LeafletMap = BaseMap.extend({
|
||||||
this.initControls()
|
this.initControls()
|
||||||
// Needs locate control and hash to exist
|
// Needs locate control and hash to exist
|
||||||
this.initCenter()
|
this.initCenter()
|
||||||
this.update()
|
this.renderUI()
|
||||||
},
|
},
|
||||||
|
|
||||||
update: function () {
|
renderUI: function () {
|
||||||
this.setOptions(this.umap.properties)
|
setOptions(this, this._umap.properties)
|
||||||
this.initTileLayers()
|
this.initTileLayers()
|
||||||
this.renderCaptionBar()
|
this.renderCaptionBar()
|
||||||
this.renderEditToolbar()
|
this.renderEditToolbar()
|
||||||
|
@ -502,10 +489,6 @@ export const LeafletMap = BaseMap.extend({
|
||||||
this.handleLimitBounds()
|
this.handleLimitBounds()
|
||||||
},
|
},
|
||||||
|
|
||||||
setOptions: function (options) {
|
|
||||||
setOptions(this, options)
|
|
||||||
},
|
|
||||||
|
|
||||||
closeInplaceToolbar: function () {
|
closeInplaceToolbar: function () {
|
||||||
const toolbar = this._toolbars[L.Toolbar.Popup._toolbar_class_id]
|
const toolbar = this._toolbars[L.Toolbar.Popup._toolbar_class_id]
|
||||||
if (toolbar) toolbar.remove()
|
if (toolbar) toolbar.remove()
|
||||||
|
@ -534,11 +517,11 @@ export const LeafletMap = BaseMap.extend({
|
||||||
} else if (this.options.defaultView === 'locate' && !this.options.noControl) {
|
} else if (this.options.defaultView === 'locate' && !this.options.noControl) {
|
||||||
this._controls.locate.start()
|
this._controls.locate.start()
|
||||||
} else if (this.options.defaultView === 'data') {
|
} else if (this.options.defaultView === 'data') {
|
||||||
this.umap.onceDataLoaded(this.umap.fitDataBounds)
|
this._umap.onceDataLoaded(this._umap.fitDataBounds)
|
||||||
} else if (this.options.defaultView === 'latest') {
|
} else if (this.options.defaultView === 'latest') {
|
||||||
this.umap.onceDataLoaded(() => {
|
this._umap.onceDataLoaded(() => {
|
||||||
if (!this.umap.hasData()) return
|
if (!this._umap.hasData()) return
|
||||||
const datalayer = this.umap.firstVisibleDatalayer()
|
const datalayer = this._umap.firstVisibleDatalayer()
|
||||||
let feature
|
let feature
|
||||||
if (datalayer) {
|
if (datalayer) {
|
||||||
const feature = datalayer.getFeatureByIndex(-1)
|
const feature = datalayer.getFeatureByIndex(-1)
|
||||||
|
@ -590,4 +573,9 @@ export const LeafletMap = BaseMap.extend({
|
||||||
}
|
}
|
||||||
return BaseMap.prototype.setMaxBounds.call(this, bounds)
|
return BaseMap.prototype.setMaxBounds.call(this, bounds)
|
||||||
},
|
},
|
||||||
|
|
||||||
|
initEditTools: function () {
|
||||||
|
this.editTools = new U.Editable(this._umap)
|
||||||
|
this.renderEditToolbar()
|
||||||
|
},
|
||||||
})
|
})
|
||||||
|
|
|
@ -61,15 +61,15 @@ const Panel = Popup.extend({
|
||||||
zoomAnimation: false,
|
zoomAnimation: false,
|
||||||
},
|
},
|
||||||
|
|
||||||
onAdd: function (map) {
|
onAdd: function (leafletMap) {
|
||||||
map.umap.panel.setDefaultMode('expanded')
|
leafletMap._umap.panel.setDefaultMode('expanded')
|
||||||
map.umap.panel.open({
|
leafletMap._umap.panel.open({
|
||||||
content: this._content,
|
content: this._content,
|
||||||
actions: [Browser.backButton(map)],
|
actions: [Browser.backButton(leafletMap._umap)],
|
||||||
})
|
})
|
||||||
|
|
||||||
// fire events as in base class Popup.js:onAdd
|
// fire events as in base class Popup.js:onAdd
|
||||||
map.fire('popupopen', { popup: this })
|
leafletMap.fire('popupopen', { popup: this })
|
||||||
if (this._source) {
|
if (this._source) {
|
||||||
this._source.fire('popupopen', { popup: this }, true)
|
this._source.fire('popupopen', { popup: this }, true)
|
||||||
if (!(this._source instanceof Path)) {
|
if (!(this._source instanceof Path)) {
|
||||||
|
@ -78,11 +78,11 @@ const Panel = Popup.extend({
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onRemove: function (map) {
|
onRemove: function (leafletMap) {
|
||||||
map.umap.panel.close()
|
leafletMap._umap.panel.close()
|
||||||
|
|
||||||
// fire events as in base class Popup.js:onRemove
|
// fire events as in base class Popup.js:onRemove
|
||||||
map.fire('popupclose', { popup: this })
|
leafletMap.fire('popupclose', { popup: this })
|
||||||
if (this._source) {
|
if (this._source) {
|
||||||
this._source.fire('popupclose', { popup: this }, true)
|
this._source.fire('popupclose', { popup: this }, true)
|
||||||
if (!(this._source instanceof Path)) {
|
if (!(this._source instanceof Path)) {
|
||||||
|
|
|
@ -52,7 +52,7 @@ const FeatureMixin = {
|
||||||
onClick: function (event) {
|
onClick: function (event) {
|
||||||
if (this._map.measureTools?.enabled()) return
|
if (this._map.measureTools?.enabled()) return
|
||||||
this._popupHandlersAdded = true // Prevent leaflet from managing event
|
this._popupHandlersAdded = true // Prevent leaflet from managing event
|
||||||
if (!this._map.umap.editEnabled) {
|
if (!this._map._umap.editEnabled) {
|
||||||
this.feature.view(event)
|
this.feature.view(event)
|
||||||
} else if (!this.feature.isReadOnly()) {
|
} else if (!this.feature.isReadOnly()) {
|
||||||
if (event.originalEvent.shiftKey) {
|
if (event.originalEvent.shiftKey) {
|
||||||
|
@ -96,8 +96,8 @@ const FeatureMixin = {
|
||||||
DomEvent.stop(event)
|
DomEvent.stop(event)
|
||||||
const items = this.feature
|
const items = this.feature
|
||||||
.getContextMenuItems(event)
|
.getContextMenuItems(event)
|
||||||
.concat(this._map.umap.getContextMenuItems(event))
|
.concat(this._map._umap.getSharedContextMenuItems(event))
|
||||||
this._map.umap.contextmenu.open(event.originalEvent, items)
|
this._map._umap.contextmenu.open(event.originalEvent, items)
|
||||||
},
|
},
|
||||||
|
|
||||||
onCommit: function () {
|
onCommit: function () {
|
||||||
|
@ -134,7 +134,7 @@ const PointMixin = {
|
||||||
|
|
||||||
_enableDragging: function () {
|
_enableDragging: function () {
|
||||||
// TODO: start dragging after 1 second on mouse down
|
// TODO: start dragging after 1 second on mouse down
|
||||||
if (this._map.umap.editEnabled) {
|
if (this._map._umap.editEnabled) {
|
||||||
if (!this.editEnabled()) this.enableEdit()
|
if (!this.editEnabled()) this.enableEdit()
|
||||||
// Enabling dragging on the marker override the Draggable._OnDown
|
// Enabling dragging on the marker override the Draggable._OnDown
|
||||||
// event, which, as it stopPropagation, refrain the call of
|
// event, which, as it stopPropagation, refrain the call of
|
||||||
|
@ -146,7 +146,7 @@ const PointMixin = {
|
||||||
},
|
},
|
||||||
|
|
||||||
_disableDragging: function () {
|
_disableDragging: function () {
|
||||||
if (this._map.umap.editEnabled) {
|
if (this._map._umap.editEnabled) {
|
||||||
if (this.editor?.drawing) return // when creating a new marker, the mouse can trigger the mouseover/mouseout event
|
if (this.editor?.drawing) return // when creating a new marker, the mouse can trigger the mouseover/mouseout event
|
||||||
// do not listen to them
|
// do not listen to them
|
||||||
this.disableEdit()
|
this.disableEdit()
|
||||||
|
@ -253,21 +253,21 @@ export const LeafletMarker = Marker.extend({
|
||||||
const PathMixin = {
|
const PathMixin = {
|
||||||
_onMouseOver: function () {
|
_onMouseOver: function () {
|
||||||
if (this._map.measureTools?.enabled()) {
|
if (this._map.measureTools?.enabled()) {
|
||||||
this._map.umap.tooltip.open({ content: this.getMeasure(), anchor: this })
|
this._map._umap.tooltip.open({ content: this.getMeasure(), anchor: this })
|
||||||
} else if (this._map.umap.editEnabled && !this._map.umap.editedFeature) {
|
} else if (this._map._umap.editEnabled && !this._map._umap.editedFeature) {
|
||||||
this._map.umap.tooltip.open({ content: translate('Click to edit'), anchor: this })
|
this._map._umap.tooltip.open({ content: translate('Click to edit'), anchor: this })
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
makeGeometryEditable: function () {
|
makeGeometryEditable: function () {
|
||||||
if (this._map.umap.editedFeature !== this.feature) {
|
if (this._map._umap.editedFeature !== this.feature) {
|
||||||
this.disableEdit()
|
this.disableEdit()
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
this._map.once('moveend', this.makeGeometryEditable, this)
|
this._map.once('moveend', this.makeGeometryEditable, this)
|
||||||
const pointsCount = this._parts.reduce((acc, part) => acc + part.length, 0)
|
const pointsCount = this._parts.reduce((acc, part) => acc + part.length, 0)
|
||||||
if (pointsCount > 100 && this._map.getZoom() < this._map.getMaxZoom()) {
|
if (pointsCount > 100 && this._map.getZoom() < this._map.getMaxZoom()) {
|
||||||
this._map.umap.tooltip.open({ content: L._('Please zoom in to edit the geometry') })
|
this._map._umap.tooltip.open({ content: L._('Please zoom in to edit the geometry') })
|
||||||
this.disableEdit()
|
this.disableEdit()
|
||||||
} else {
|
} else {
|
||||||
this.enableEdit()
|
this.enableEdit()
|
||||||
|
|
|
@ -22,7 +22,7 @@ class Rule {
|
||||||
|
|
||||||
set isDirty(status) {
|
set isDirty(status) {
|
||||||
this._isDirty = status
|
this._isDirty = status
|
||||||
if (status) this.umap.isDirty = status
|
if (status) this._umap.isDirty = status
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(umap, condition = '', options = {}) {
|
constructor(umap, condition = '', options = {}) {
|
||||||
|
@ -38,14 +38,14 @@ class Rule {
|
||||||
['!=', this.not_equal],
|
['!=', this.not_equal],
|
||||||
['=', this.equal],
|
['=', this.equal],
|
||||||
]
|
]
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.active = true
|
this.active = true
|
||||||
this.options = options
|
this.options = options
|
||||||
this.condition = condition
|
this.condition = condition
|
||||||
}
|
}
|
||||||
|
|
||||||
render(fields) {
|
render(fields) {
|
||||||
this.umap.render(fields)
|
this._umap.render(fields)
|
||||||
}
|
}
|
||||||
|
|
||||||
equal(other) {
|
equal(other) {
|
||||||
|
@ -102,10 +102,6 @@ class Rule {
|
||||||
return this.operator(this.cast(props[this.key]))
|
return this.operator(this.cast(props[this.key]))
|
||||||
}
|
}
|
||||||
|
|
||||||
getMap() {
|
|
||||||
return this.umap
|
|
||||||
}
|
|
||||||
|
|
||||||
getOption(option) {
|
getOption(option) {
|
||||||
return this.options[option]
|
return this.options[option]
|
||||||
}
|
}
|
||||||
|
@ -137,7 +133,7 @@ class Rule {
|
||||||
const defaultShapeProperties = DomUtil.add('div', '', container)
|
const defaultShapeProperties = DomUtil.add('div', '', container)
|
||||||
defaultShapeProperties.appendChild(builder.build())
|
defaultShapeProperties.appendChild(builder.build())
|
||||||
const autocomplete = new AutocompleteDatalist(builder.helpers.condition.input)
|
const autocomplete = new AutocompleteDatalist(builder.helpers.condition.input)
|
||||||
const properties = this.umap.allProperties()
|
const properties = this._umap.allProperties()
|
||||||
autocomplete.suggestions = properties
|
autocomplete.suggestions = properties
|
||||||
autocomplete.input.addEventListener('input', (event) => {
|
autocomplete.input.addEventListener('input', (event) => {
|
||||||
const value = event.target.value
|
const value = event.target.value
|
||||||
|
@ -145,12 +141,12 @@ class Rule {
|
||||||
autocomplete.suggestions = [`${value}=`, `${value}!=`, `${value}>`, `${value}<`]
|
autocomplete.suggestions = [`${value}=`, `${value}!=`, `${value}>`, `${value}<`]
|
||||||
} else if (value.endsWith('=')) {
|
} else if (value.endsWith('=')) {
|
||||||
const key = value.split('!')[0].split('=')[0]
|
const key = value.split('!')[0].split('=')[0]
|
||||||
autocomplete.suggestions = this.umap
|
autocomplete.suggestions = this._umap
|
||||||
.sortedValues(key)
|
.sortedValues(key)
|
||||||
.map((str) => `${value}${str || ''}`)
|
.map((str) => `${value}${str || ''}`)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
this.umap.editPanel.open({ content: container })
|
this._umap.editPanel.open({ content: container })
|
||||||
}
|
}
|
||||||
|
|
||||||
renderToolbox(row) {
|
renderToolbox(row) {
|
||||||
|
@ -177,7 +173,7 @@ class Rule {
|
||||||
function () {
|
function () {
|
||||||
if (!confirm(translate('Are you sure you want to delete this rule?'))) return
|
if (!confirm(translate('Are you sure you want to delete this rule?'))) return
|
||||||
this._delete()
|
this._delete()
|
||||||
this.umap.editPanel.close()
|
this._umap.editPanel.close()
|
||||||
},
|
},
|
||||||
this
|
this
|
||||||
)
|
)
|
||||||
|
@ -187,27 +183,27 @@ class Rule {
|
||||||
DomEvent.on(toggle, 'click', () => {
|
DomEvent.on(toggle, 'click', () => {
|
||||||
this.active = !this.active
|
this.active = !this.active
|
||||||
row.classList.toggle('off', !this.active)
|
row.classList.toggle('off', !this.active)
|
||||||
this.umap.render(['rules'])
|
this._umap.render(['rules'])
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
_delete() {
|
_delete() {
|
||||||
this.umap.rules.rules = this.umap.rules.rules.filter((rule) => rule !== this)
|
this._umap.rules.rules = this._umap.rules.rules.filter((rule) => rule !== this)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default class Rules {
|
export default class Rules {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.rules = []
|
this.rules = []
|
||||||
this.loadRules()
|
this.loadRules()
|
||||||
}
|
}
|
||||||
|
|
||||||
loadRules() {
|
loadRules() {
|
||||||
if (!this.umap.properties.rules?.length) return
|
if (!this._umap.properties.rules?.length) return
|
||||||
for (const { condition, options } of this.umap.properties.rules) {
|
for (const { condition, options } of this._umap.properties.rules) {
|
||||||
if (!condition) continue
|
if (!condition) continue
|
||||||
this.rules.push(new Rule(this.umap, condition, options))
|
this.rules.push(new Rule(this._umap, condition, options))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -226,7 +222,7 @@ export default class Rules {
|
||||||
else newIdx = referenceIdx + 1
|
else newIdx = referenceIdx + 1
|
||||||
this.rules.splice(newIdx, 0, moved)
|
this.rules.splice(newIdx, 0, moved)
|
||||||
moved.isDirty = true
|
moved.isDirty = true
|
||||||
this.umap.render(['rules'])
|
this._umap.render(['rules'])
|
||||||
}
|
}
|
||||||
|
|
||||||
edit(container) {
|
edit(container) {
|
||||||
|
@ -244,14 +240,14 @@ export default class Rules {
|
||||||
}
|
}
|
||||||
|
|
||||||
addRule() {
|
addRule() {
|
||||||
const rule = new Rule(this.umap)
|
const rule = new Rule(this._umap)
|
||||||
rule.isDirty = true
|
rule.isDirty = true
|
||||||
this.rules.push(rule)
|
this.rules.push(rule)
|
||||||
rule.edit(map)
|
rule.edit(map)
|
||||||
}
|
}
|
||||||
|
|
||||||
commit() {
|
commit() {
|
||||||
this.umap.properties.rules = this.rules.map((rule) => {
|
this._umap.properties.rules = this.rules.map((rule) => {
|
||||||
return {
|
return {
|
||||||
condition: rule.condition,
|
condition: rule.condition,
|
||||||
options: rule.options,
|
options: rule.options,
|
||||||
|
|
|
@ -10,21 +10,21 @@ export async function save() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function add(obj) {
|
function add(obj) {
|
||||||
_queue.add(obj)
|
_queue.add(obj)
|
||||||
_onUpdate()
|
onUpdate()
|
||||||
}
|
}
|
||||||
|
|
||||||
export function remove(obj) {
|
function remove(obj) {
|
||||||
_queue.delete(obj)
|
_queue.delete(obj)
|
||||||
_onUpdate()
|
onUpdate()
|
||||||
}
|
}
|
||||||
|
|
||||||
export function has(obj) {
|
function has(obj) {
|
||||||
return _queue.has(obj)
|
return _queue.has(obj)
|
||||||
}
|
}
|
||||||
|
|
||||||
function _onUpdate() {
|
function onUpdate() {
|
||||||
isDirty = Boolean(_queue.size)
|
isDirty = Boolean(_queue.size)
|
||||||
document.body.classList.toggle('umap-is-dirty', isDirty)
|
document.body.classList.toggle('umap-is-dirty', isDirty)
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,7 +5,7 @@ import * as Utils from './utils.js'
|
||||||
|
|
||||||
export default class Share {
|
export default class Share {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
}
|
}
|
||||||
|
|
||||||
build() {
|
build() {
|
||||||
|
@ -22,11 +22,11 @@ export default class Share {
|
||||||
window.location.protocol + Utils.getBaseUrl()
|
window.location.protocol + Utils.getBaseUrl()
|
||||||
)
|
)
|
||||||
|
|
||||||
if (this.umap.properties.shortUrl) {
|
if (this._umap.properties.shortUrl) {
|
||||||
DomUtil.createCopiableInput(
|
DomUtil.createCopiableInput(
|
||||||
this.container,
|
this.container,
|
||||||
translate('Short link'),
|
translate('Short link'),
|
||||||
this.umap.properties.shortUrl
|
this._umap.properties.shortUrl
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -60,8 +60,8 @@ export default class Share {
|
||||||
this.container,
|
this.container,
|
||||||
translate('All data and settings of the map')
|
translate('All data and settings of the map')
|
||||||
)
|
)
|
||||||
const downloadUrl = this.umap.urls.get('map_download', {
|
const downloadUrl = this._umap.urls.get('map_download', {
|
||||||
map_id: this.umap.properties.umap_id,
|
map_id: this._umap.properties.umap_id,
|
||||||
})
|
})
|
||||||
const link = Utils.loadTemplate(`
|
const link = Utils.loadTemplate(`
|
||||||
<div>
|
<div>
|
||||||
|
@ -116,10 +116,10 @@ export default class Share {
|
||||||
'queryString.captionMenus',
|
'queryString.captionMenus',
|
||||||
]
|
]
|
||||||
// TODO: move HIDDABLE_CONTROLS to SCHEMA ?
|
// TODO: move HIDDABLE_CONTROLS to SCHEMA ?
|
||||||
for (const name of this.umap._leafletMap.HIDDABLE_CONTROLS) {
|
for (const name of this._umap._leafletMap.HIDDABLE_CONTROLS) {
|
||||||
UIFields.push(`queryString.${name}Control`)
|
UIFields.push(`queryString.${name}Control`)
|
||||||
}
|
}
|
||||||
const iframeExporter = new IframeExporter(this.umap)
|
const iframeExporter = new IframeExporter(this._umap)
|
||||||
const buildIframeCode = () => {
|
const buildIframeCode = () => {
|
||||||
iframe.textContent = iframeExporter.build()
|
iframe.textContent = iframeExporter.build()
|
||||||
exportUrl.value = window.location.protocol + iframeExporter.buildUrl()
|
exportUrl.value = window.location.protocol + iframeExporter.buildUrl()
|
||||||
|
@ -137,13 +137,13 @@ export default class Share {
|
||||||
|
|
||||||
open() {
|
open() {
|
||||||
if (!this.container) this.build()
|
if (!this.container) this.build()
|
||||||
this.umap.panel.open({ content: this.container })
|
this._umap.panel.open({ content: this.container })
|
||||||
}
|
}
|
||||||
|
|
||||||
async format(mode) {
|
async format(mode) {
|
||||||
const type = EXPORT_FORMATS[mode]
|
const type = EXPORT_FORMATS[mode]
|
||||||
const content = await type.formatter(this.umap)
|
const content = await type.formatter(this._umap)
|
||||||
const filename = Utils.slugify(this.umap.properties.name) + type.ext
|
const filename = Utils.slugify(this._umap.properties.name) + type.ext
|
||||||
return { content, filetype: type.filetype, filename }
|
return { content, filetype: type.filetype, filename }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -163,7 +163,7 @@ export default class Share {
|
||||||
|
|
||||||
class IframeExporter {
|
class IframeExporter {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this.baseUrl = Utils.getBaseUrl()
|
this.baseUrl = Utils.getBaseUrl()
|
||||||
this.options = {
|
this.options = {
|
||||||
includeFullScreenLink: true,
|
includeFullScreenLink: true,
|
||||||
|
@ -193,18 +193,18 @@ class IframeExporter {
|
||||||
height: '300px',
|
height: '300px',
|
||||||
}
|
}
|
||||||
// Use map default, not generic default
|
// Use map default, not generic default
|
||||||
this.queryString.onLoadPanel = this.umap.getOption('onLoadPanel')
|
this.queryString.onLoadPanel = this._umap.getProperty('onLoadPanel')
|
||||||
}
|
}
|
||||||
|
|
||||||
buildUrl(options) {
|
buildUrl(options) {
|
||||||
const datalayers = []
|
const datalayers = []
|
||||||
if (this.options.viewCurrentFeature && this.umap.currentFeature) {
|
if (this.options.viewCurrentFeature && this._umap.currentFeature) {
|
||||||
this.queryString.feature = this.umap.currentFeature.getSlug()
|
this.queryString.feature = this._umap.currentFeature.getSlug()
|
||||||
} else {
|
} else {
|
||||||
delete this.queryString.feature
|
delete this.queryString.feature
|
||||||
}
|
}
|
||||||
if (this.options.keepCurrentDatalayers) {
|
if (this.options.keepCurrentDatalayers) {
|
||||||
this.umap.eachDataLayer((datalayer) => {
|
this._umap.eachDataLayer((datalayer) => {
|
||||||
if (datalayer.isVisible() && datalayer.umap_id) {
|
if (datalayer.isVisible() && datalayer.umap_id) {
|
||||||
datalayers.push(datalayer.umap_id)
|
datalayers.push(datalayer.umap_id)
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,20 +13,20 @@ const TOOLBOX_TEMPLATE = `
|
||||||
`
|
`
|
||||||
|
|
||||||
export default class Slideshow extends WithTemplate {
|
export default class Slideshow extends WithTemplate {
|
||||||
constructor(umap, options) {
|
constructor(umap, leafletMap, properties) {
|
||||||
super()
|
super()
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
this._id = null
|
this._id = null
|
||||||
this.CLASSNAME = 'umap-slideshow-active'
|
this.CLASSNAME = 'umap-slideshow-active'
|
||||||
this.setOptions(options)
|
this.setProperties(properties)
|
||||||
this._current = null
|
this._current = null
|
||||||
|
|
||||||
if (this.options.autoplay) {
|
if (this.properties.autoplay) {
|
||||||
this.umap.onceDataLoaded(function () {
|
this._umap.onceDataLoaded(function () {
|
||||||
this.play()
|
this.play()
|
||||||
}, this)
|
}, this)
|
||||||
}
|
}
|
||||||
this.umap._leafletMap.on(
|
leafletMap.on(
|
||||||
'edit:enabled',
|
'edit:enabled',
|
||||||
function () {
|
function () {
|
||||||
this.stop()
|
this.stop()
|
||||||
|
@ -54,22 +54,22 @@ export default class Slideshow extends WithTemplate {
|
||||||
return this.current.getNext()
|
return this.current.getNext()
|
||||||
}
|
}
|
||||||
|
|
||||||
setOptions(options) {
|
setProperties(properties) {
|
||||||
this.options = Object.assign(
|
this.properties = Object.assign(
|
||||||
{
|
{
|
||||||
delay: 5000,
|
delay: 5000,
|
||||||
autoplay: false,
|
autoplay: false,
|
||||||
},
|
},
|
||||||
options
|
properties
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
defaultDatalayer() {
|
defaultDatalayer() {
|
||||||
return this.umap.findDataLayer((d) => d.canBrowse())
|
return this._umap.findDataLayer((d) => d.canBrowse())
|
||||||
}
|
}
|
||||||
|
|
||||||
startSpinner() {
|
startSpinner() {
|
||||||
const time = Number.parseInt(this.options.delay, 10)
|
const time = Number.parseInt(this.properties.delay, 10)
|
||||||
if (!time) return
|
if (!time) return
|
||||||
const css = `rotation ${time / 1000}s infinite linear`
|
const css = `rotation ${time / 1000}s infinite linear`
|
||||||
const spinner = document.querySelector('.umap-slideshow-toolbox .play .spinner')
|
const spinner = document.querySelector('.umap-slideshow-toolbox .play .spinner')
|
||||||
|
@ -83,9 +83,9 @@ export default class Slideshow extends WithTemplate {
|
||||||
|
|
||||||
play() {
|
play() {
|
||||||
if (this._id) return
|
if (this._id) return
|
||||||
if (this.umap.editEnabled || !this.umap.properties.slideshow.active) return
|
if (this._umap.editEnabled || !this._umap.properties.slideshow.active) return
|
||||||
L.DomUtil.addClass(document.body, this.CLASSNAME)
|
L.DomUtil.addClass(document.body, this.CLASSNAME)
|
||||||
this._id = window.setInterval(L.bind(this.loop, this), this.options.delay)
|
this._id = window.setInterval(L.bind(this.loop, this), this.properties.delay)
|
||||||
this.startSpinner()
|
this.startSpinner()
|
||||||
this.loop()
|
this.loop()
|
||||||
}
|
}
|
||||||
|
@ -123,7 +123,7 @@ export default class Slideshow extends WithTemplate {
|
||||||
|
|
||||||
step() {
|
step() {
|
||||||
if (!this.current) return this.stop()
|
if (!this.current) return this.stop()
|
||||||
this.current.zoomTo({ easing: this.options.easing })
|
this.current.zoomTo({ easing: this.properties.easing })
|
||||||
this.current.view()
|
this.current.view()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -7,7 +7,7 @@ import { fieldInSchema } from '../utils.js'
|
||||||
|
|
||||||
class BaseUpdater {
|
class BaseUpdater {
|
||||||
constructor(umap) {
|
constructor(umap) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
}
|
}
|
||||||
|
|
||||||
updateObjectValue(obj, key, value) {
|
updateObjectValue(obj, key, value) {
|
||||||
|
@ -32,8 +32,8 @@ class BaseUpdater {
|
||||||
}
|
}
|
||||||
|
|
||||||
getDataLayerFromID(layerId) {
|
getDataLayerFromID(layerId) {
|
||||||
if (layerId) return this.umap.getDataLayerByUmapId(layerId)
|
if (layerId) return this._umap.getDataLayerByUmapId(layerId)
|
||||||
return this.umap.defaultEditDataLayer()
|
return this._umap.defaultEditDataLayer()
|
||||||
}
|
}
|
||||||
|
|
||||||
applyMessage(payload) {
|
applyMessage(payload) {
|
||||||
|
@ -45,18 +45,18 @@ class BaseUpdater {
|
||||||
export class MapUpdater extends BaseUpdater {
|
export class MapUpdater extends BaseUpdater {
|
||||||
update({ key, value }) {
|
update({ key, value }) {
|
||||||
if (fieldInSchema(key)) {
|
if (fieldInSchema(key)) {
|
||||||
this.updateObjectValue(this.umap, key, value)
|
this.updateObjectValue(this._umap, key, value)
|
||||||
}
|
}
|
||||||
|
|
||||||
this.umap.render([key])
|
this._umap.render([key])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class DataLayerUpdater extends BaseUpdater {
|
export class DataLayerUpdater extends BaseUpdater {
|
||||||
upsert({ value }) {
|
upsert({ value }) {
|
||||||
// Inserts does not happen (we use multiple updates instead).
|
// Inserts does not happen (we use multiple updates instead).
|
||||||
this.umap.createDataLayer(value, false)
|
this._umap.createDataLayer(value, false)
|
||||||
this.umap.render([])
|
this._umap.render([])
|
||||||
}
|
}
|
||||||
|
|
||||||
update({ key, metadata, value }) {
|
update({ key, metadata, value }) {
|
||||||
|
|
|
@ -14,10 +14,11 @@ const TEMPLATE = `
|
||||||
`
|
`
|
||||||
|
|
||||||
export default class TableEditor extends WithTemplate {
|
export default class TableEditor extends WithTemplate {
|
||||||
constructor(datalayer) {
|
constructor(umap, datalayer, leafletMap) {
|
||||||
super()
|
super()
|
||||||
this.datalayer = datalayer
|
this.datalayer = datalayer
|
||||||
this.umap = this.datalayer.umap
|
this._umap = umap
|
||||||
|
this._leafletMap = leafletMap
|
||||||
this.contextmenu = new ContextMenu({ className: 'dark' })
|
this.contextmenu = new ContextMenu({ className: 'dark' })
|
||||||
this.table = this.loadTemplate(TEMPLATE)
|
this.table = this.loadTemplate(TEMPLATE)
|
||||||
if (!this.datalayer.isRemoteLayer()) {
|
if (!this.datalayer.isRemoteLayer()) {
|
||||||
|
@ -36,20 +37,20 @@ export default class TableEditor extends WithTemplate {
|
||||||
openHeaderMenu(property) {
|
openHeaderMenu(property) {
|
||||||
const actions = []
|
const actions = []
|
||||||
let filterItem
|
let filterItem
|
||||||
if (this.umap.facets.has(property)) {
|
if (this._umap.facets.has(property)) {
|
||||||
filterItem = {
|
filterItem = {
|
||||||
label: translate('Remove filter for this column'),
|
label: translate('Remove filter for this column'),
|
||||||
action: () => {
|
action: () => {
|
||||||
this.umap.facets.remove(property)
|
this._umap.facets.remove(property)
|
||||||
this.umap.browser.open('filters')
|
this._umap.browser.open('filters')
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
filterItem = {
|
filterItem = {
|
||||||
label: translate('Add filter for this column'),
|
label: translate('Add filter for this column'),
|
||||||
action: () => {
|
action: () => {
|
||||||
this.umap.facets.add(property)
|
this._umap.facets.add(property)
|
||||||
this.umap.browser.open('filters')
|
this._umap.browser.open('filters')
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -86,8 +87,8 @@ export default class TableEditor extends WithTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
renderBody() {
|
renderBody() {
|
||||||
const bounds = this.umap._leafletMap.getBounds()
|
const bounds = this._leafletMap.getBounds()
|
||||||
const inBbox = this.umap.browser.options.inBbox
|
const inBbox = this._umap.browser.options.inBbox
|
||||||
let html = ''
|
let html = ''
|
||||||
this.datalayer.eachFeature((feature) => {
|
this.datalayer.eachFeature((feature) => {
|
||||||
if (feature.isFiltered()) return
|
if (feature.isFiltered()) return
|
||||||
|
@ -121,7 +122,7 @@ export default class TableEditor extends WithTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
renameProperty(property) {
|
renameProperty(property) {
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.prompt(translate('Please enter the new name of this property'))
|
.prompt(translate('Please enter the new name of this property'))
|
||||||
.then(({ prompt }) => {
|
.then(({ prompt }) => {
|
||||||
if (!prompt || !this.validateName(prompt)) return
|
if (!prompt || !this.validateName(prompt)) return
|
||||||
|
@ -135,7 +136,7 @@ export default class TableEditor extends WithTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
deleteProperty(property) {
|
deleteProperty(property) {
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.confirm(
|
.confirm(
|
||||||
translate('Are you sure you want to delete this property on all the features?')
|
translate('Are you sure you want to delete this property on all the features?')
|
||||||
)
|
)
|
||||||
|
@ -150,7 +151,7 @@ export default class TableEditor extends WithTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
addProperty() {
|
addProperty() {
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.prompt(translate('Please enter the name of the property'))
|
.prompt(translate('Please enter the name of the property'))
|
||||||
.then(({ prompt }) => {
|
.then(({ prompt }) => {
|
||||||
if (!prompt || !this.validateName(prompt)) return
|
if (!prompt || !this.validateName(prompt)) return
|
||||||
|
@ -187,10 +188,10 @@ export default class TableEditor extends WithTemplate {
|
||||||
<button class="flat" type="button" data-ref="filters">
|
<button class="flat" type="button" data-ref="filters">
|
||||||
<i class="icon icon-16 icon-filters"></i>${translate('Filter data')}
|
<i class="icon icon-16 icon-filters"></i>${translate('Filter data')}
|
||||||
</button>`)
|
</button>`)
|
||||||
filterButton.addEventListener('click', () => this.umap.browser.open('filters'))
|
filterButton.addEventListener('click', () => this._umap.browser.open('filters'))
|
||||||
actions.push(filterButton)
|
actions.push(filterButton)
|
||||||
|
|
||||||
this.umap.fullPanel.open({
|
this._umap.fullPanel.open({
|
||||||
content: this.table,
|
content: this.table,
|
||||||
className: 'umap-table-editor',
|
className: 'umap-table-editor',
|
||||||
actions: actions,
|
actions: actions,
|
||||||
|
@ -304,7 +305,7 @@ export default class TableEditor extends WithTemplate {
|
||||||
deleteRows() {
|
deleteRows() {
|
||||||
const selectedRows = this.getSelectedRows()
|
const selectedRows = this.getSelectedRows()
|
||||||
if (!selectedRows.length) return
|
if (!selectedRows.length) return
|
||||||
this.umap.dialog
|
this._umap.dialog
|
||||||
.confirm(
|
.confirm(
|
||||||
translate('Found {count} rows. Are you sure you want to delete all?', {
|
translate('Found {count} rows. Are you sure you want to delete all?', {
|
||||||
count: selectedRows.length,
|
count: selectedRows.length,
|
||||||
|
@ -320,9 +321,9 @@ export default class TableEditor extends WithTemplate {
|
||||||
this.datalayer.show()
|
this.datalayer.show()
|
||||||
this.datalayer.dataChanged()
|
this.datalayer.dataChanged()
|
||||||
this.renderBody()
|
this.renderBody()
|
||||||
if (this.umap.browser.isOpen()) {
|
if (this._umap.browser.isOpen()) {
|
||||||
this.umap.browser.resetFilters()
|
this._umap.browser.resetFilters()
|
||||||
this.umap.browser.open('filters')
|
this._umap.browser.open('filters')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,9 +2,10 @@ import { DomEvent, DomUtil } from '../../../vendors/leaflet/leaflet-src.esm.js'
|
||||||
import { translate } from '../i18n.js'
|
import { translate } from '../i18n.js'
|
||||||
|
|
||||||
export class Panel {
|
export class Panel {
|
||||||
constructor(umap) {
|
constructor(umap, leafletMap) {
|
||||||
this.parent = umap._leafletMap._controlContainer
|
this.parent = leafletMap._controlContainer
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
|
this._leafletMap = leafletMap
|
||||||
this.container = DomUtil.create('div', '', this.parent)
|
this.container = DomUtil.create('div', '', this.parent)
|
||||||
// This will be set once according to the panel configurated at load
|
// This will be set once according to the panel configurated at load
|
||||||
// or by using panels as popups
|
// or by using panels as popups
|
||||||
|
@ -80,26 +81,26 @@ export class Panel {
|
||||||
onClose() {
|
onClose() {
|
||||||
if (DomUtil.hasClass(this.container, 'on')) {
|
if (DomUtil.hasClass(this.container, 'on')) {
|
||||||
DomUtil.removeClass(this.container, 'on')
|
DomUtil.removeClass(this.container, 'on')
|
||||||
this.umap._leafletMap.invalidateSize({ pan: false })
|
this._leafletMap.invalidateSize({ pan: false })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class EditPanel extends Panel {
|
export class EditPanel extends Panel {
|
||||||
constructor(umap) {
|
constructor(umap, leafletMap) {
|
||||||
super(umap)
|
super(umap, leafletMap)
|
||||||
this.className = 'right dark'
|
this.className = 'right dark'
|
||||||
}
|
}
|
||||||
|
|
||||||
onClose() {
|
onClose() {
|
||||||
super.onClose()
|
super.onClose()
|
||||||
this.umap.editedFeature = null
|
this._umap.editedFeature = null
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class FullPanel extends Panel {
|
export class FullPanel extends Panel {
|
||||||
constructor(umap) {
|
constructor(umap, leafletMap) {
|
||||||
super(umap)
|
super(umap, leafletMap)
|
||||||
this.className = 'full dark'
|
this.className = 'full dark'
|
||||||
this.mode = 'expanded'
|
this.mode = 'expanded'
|
||||||
}
|
}
|
||||||
|
|
|
@ -90,26 +90,25 @@ export default class Umap extends ServerStored {
|
||||||
// Needed to render controls
|
// Needed to render controls
|
||||||
this.permissions = new MapPermissions(this)
|
this.permissions = new MapPermissions(this)
|
||||||
this.urls = new URLs(this.properties.urls)
|
this.urls = new URLs(this.properties.urls)
|
||||||
this.slideshow = new Slideshow(this, this.properties.slideshow)
|
this.slideshow = new Slideshow(this, this._leafletMap, this.properties.slideshow)
|
||||||
|
|
||||||
this._leafletMap.setup()
|
this._leafletMap.setup()
|
||||||
|
|
||||||
if (geojson.properties.schema) this.overrideSchema(geojson.properties.schema)
|
if (geojson.properties.schema) this.overrideSchema(geojson.properties.schema)
|
||||||
|
|
||||||
|
this.panel = new Panel(this, this._leafletMap)
|
||||||
this.panel = new Panel(this)
|
|
||||||
this.dialog = new Dialog({ className: 'dark' })
|
this.dialog = new Dialog({ className: 'dark' })
|
||||||
this.tooltip = new Tooltip(this._leafletMap._controlContainer)
|
this.tooltip = new Tooltip(this._leafletMap._controlContainer)
|
||||||
this.contextmenu = new ContextMenu()
|
this.contextmenu = new ContextMenu()
|
||||||
if (this.hasEditMode()) {
|
if (this.hasEditMode()) {
|
||||||
this.editPanel = new EditPanel(this)
|
this.editPanel = new EditPanel(this, this._leafletMap)
|
||||||
this.fullPanel = new FullPanel(this)
|
this.fullPanel = new FullPanel(this, this._leafletMap)
|
||||||
}
|
}
|
||||||
this.server = new ServerRequest()
|
this.server = new ServerRequest()
|
||||||
this.request = new Request()
|
this.request = new Request()
|
||||||
this.facets = new Facets(this)
|
this.facets = new Facets(this)
|
||||||
this.browser = new Browser(this)
|
this.browser = new Browser(this, this._leafletMap)
|
||||||
this.caption = new Caption(this)
|
this.caption = new Caption(this, this._leafletMap)
|
||||||
this.importer = new Importer(this)
|
this.importer = new Importer(this)
|
||||||
this.share = new Share(this)
|
this.share = new Share(this)
|
||||||
this.rules = new Rules(this)
|
this.rules = new Rules(this)
|
||||||
|
@ -183,7 +182,7 @@ export default class Umap extends ServerStored {
|
||||||
|
|
||||||
if (!this.properties.noControl) {
|
if (!this.properties.noControl) {
|
||||||
this.initShortcuts()
|
this.initShortcuts()
|
||||||
this._leafletMap.on('contextmenu', this.onContextMenu)
|
this._leafletMap.on('contextmenu', (e) => this.onContextMenu(e))
|
||||||
this.onceDataLoaded(this.setViewFromQueryString)
|
this.onceDataLoaded(this.setViewFromQueryString)
|
||||||
this.propagate()
|
this.propagate()
|
||||||
}
|
}
|
||||||
|
@ -201,7 +200,7 @@ export default class Umap extends ServerStored {
|
||||||
this._editedFeature.endEdit()
|
this._editedFeature.endEdit()
|
||||||
}
|
}
|
||||||
this._editedFeature = feature
|
this._editedFeature = feature
|
||||||
this._leafletMap.fire('seteditedfeature')
|
this.fire('seteditedfeature')
|
||||||
}
|
}
|
||||||
|
|
||||||
setPropertiesFromQueryString() {
|
setPropertiesFromQueryString() {
|
||||||
|
@ -227,7 +226,7 @@ export default class Umap extends ServerStored {
|
||||||
// FIXME retrocompat
|
// FIXME retrocompat
|
||||||
asBoolean('displayDataBrowserOnLoad')
|
asBoolean('displayDataBrowserOnLoad')
|
||||||
asBoolean('displayCaptionOnLoad')
|
asBoolean('displayCaptionOnLoad')
|
||||||
for (const [key, schema] of Object.entries(U.SCHEMA)) {
|
for (const [key, schema] of Object.entries(SCHEMA)) {
|
||||||
switch (schema.type) {
|
switch (schema.type) {
|
||||||
case Boolean:
|
case Boolean:
|
||||||
if (schema.nullable) asNullableBoolean(key)
|
if (schema.nullable) asNullableBoolean(key)
|
||||||
|
@ -299,7 +298,7 @@ export default class Umap extends ServerStored {
|
||||||
if (dataUrls.length) {
|
if (dataUrls.length) {
|
||||||
for (let dataUrl of dataUrls) {
|
for (let dataUrl of dataUrls) {
|
||||||
dataUrl = decodeURIComponent(dataUrl)
|
dataUrl = decodeURIComponent(dataUrl)
|
||||||
dataUrl = this.localizeUrl(dataUrl)
|
dataUrl = this.renderUrl(dataUrl)
|
||||||
dataUrl = this.proxyUrl(dataUrl)
|
dataUrl = this.proxyUrl(dataUrl)
|
||||||
const datalayer = this.createDataLayer()
|
const datalayer = this.createDataLayer()
|
||||||
await datalayer.importFromUrl(dataUrl, dataFormat)
|
await datalayer.importFromUrl(dataUrl, dataFormat)
|
||||||
|
@ -383,7 +382,7 @@ export default class Umap extends ServerStored {
|
||||||
return items
|
return items
|
||||||
}
|
}
|
||||||
|
|
||||||
getContextMenuItems(event) {
|
getSharedContextMenuItems(event) {
|
||||||
const items = []
|
const items = []
|
||||||
if (this.properties.urls.routing) {
|
if (this.properties.urls.routing) {
|
||||||
items.push('-', {
|
items.push('-', {
|
||||||
|
@ -402,7 +401,7 @@ export default class Umap extends ServerStored {
|
||||||
|
|
||||||
onContextMenu(event) {
|
onContextMenu(event) {
|
||||||
const items = this.getOwnContextMenuItems(event).concat(
|
const items = this.getOwnContextMenuItems(event).concat(
|
||||||
this.getContextMenuItems(event)
|
this.getSharedContextMenuItems(event)
|
||||||
)
|
)
|
||||||
this.contextmenu.open(event.originalEvent, items)
|
this.contextmenu.open(event.originalEvent, items)
|
||||||
}
|
}
|
||||||
|
@ -424,17 +423,19 @@ export default class Umap extends ServerStored {
|
||||||
return editMode === 'simple' || editMode === 'advanced'
|
return editMode === 'simple' || editMode === 'advanced'
|
||||||
}
|
}
|
||||||
|
|
||||||
getDefaultOption(key) {
|
getProperty(key, feature) {
|
||||||
return SCHEMA[key]?.default
|
|
||||||
}
|
|
||||||
|
|
||||||
getOption(key, feature) {
|
|
||||||
if (feature) {
|
if (feature) {
|
||||||
const value = this.rules.getOption(key, feature)
|
const value = this.rules.getOption(key, feature)
|
||||||
if (value !== undefined) return value
|
if (value !== undefined) return value
|
||||||
}
|
}
|
||||||
if (Utils.usableOption(this.properties, key)) return this.properties[key]
|
if (Utils.usableOption(this.properties, key)) return this.properties[key]
|
||||||
return this.getDefaultOption(key)
|
return SCHEMA[key]?.default
|
||||||
|
}
|
||||||
|
|
||||||
|
getOption(key, feature) {
|
||||||
|
// TODO: remove when umap.forms.js is refactored and does not call blindly
|
||||||
|
// obj.getOption anymore
|
||||||
|
return this.getProperty(key, feature)
|
||||||
}
|
}
|
||||||
|
|
||||||
getGeoContext() {
|
getGeoContext() {
|
||||||
|
@ -457,7 +458,7 @@ export default class Umap extends ServerStored {
|
||||||
return context
|
return context
|
||||||
}
|
}
|
||||||
|
|
||||||
localizeUrl(url) {
|
renderUrl(url) {
|
||||||
return Utils.greedyTemplate(url, this.getGeoContext(), true)
|
return Utils.greedyTemplate(url, this.getGeoContext(), true)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -551,18 +552,18 @@ export default class Umap extends ServerStored {
|
||||||
this.createDataLayer(options, false)
|
this.createDataLayer(options, false)
|
||||||
}
|
}
|
||||||
this.datalayersLoaded = true
|
this.datalayersLoaded = true
|
||||||
this._leafletMap.fire('datalayersloaded')
|
this.fire('datalayersloaded')
|
||||||
for (const datalayer of this.datalayersIndex) {
|
for (const datalayer of this.datalayersIndex) {
|
||||||
if (datalayer.showAtLoad()) await datalayer.show()
|
if (datalayer.showAtLoad()) await datalayer.show()
|
||||||
}
|
}
|
||||||
this.dataloaded = true
|
this.dataloaded = true
|
||||||
this._leafletMap.fire('dataloaded')
|
this.fire('dataloaded')
|
||||||
}
|
}
|
||||||
|
|
||||||
createDataLayer(options = {}, sync = true) {
|
createDataLayer(options = {}, sync = true) {
|
||||||
options.name =
|
options.name =
|
||||||
options.name || `${translate('Layer')} ${this.datalayersIndex.length + 1}`
|
options.name || `${translate('Layer')} ${this.datalayersIndex.length + 1}`
|
||||||
const datalayer = new DataLayer(this, options, sync)
|
const datalayer = new DataLayer(this, this._leafletMap, options, sync)
|
||||||
|
|
||||||
if (sync !== false) {
|
if (sync !== false) {
|
||||||
datalayer.sync.upsert(datalayer.options)
|
datalayer.sync.upsert(datalayer.options)
|
||||||
|
@ -580,12 +581,6 @@ export default class Umap extends ServerStored {
|
||||||
this.onDataLayersChanged()
|
this.onDataLayersChanged()
|
||||||
}
|
}
|
||||||
|
|
||||||
redrawVisibleDataLayers() {
|
|
||||||
this.eachVisibleDataLayer((datalayer) => {
|
|
||||||
datalayer.redraw()
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
indexDatalayers() {
|
indexDatalayers() {
|
||||||
const panes = this._leafletMap.getPane('overlayPane')
|
const panes = this._leafletMap.getPane('overlayPane')
|
||||||
|
|
||||||
|
@ -631,7 +626,7 @@ export default class Umap extends ServerStored {
|
||||||
// have changed, we'll be more subtil when we'll remove the
|
// have changed, we'll be more subtil when we'll remove the
|
||||||
// save action
|
// save action
|
||||||
this.render(['name', 'user', 'permissions'])
|
this.render(['name', 'user', 'permissions'])
|
||||||
this._leafletMap.fire('saved')
|
this.fire('saved')
|
||||||
}
|
}
|
||||||
|
|
||||||
propagate() {
|
propagate() {
|
||||||
|
@ -663,13 +658,13 @@ export default class Umap extends ServerStored {
|
||||||
this._backupProperties = Object.assign({}, this.properties)
|
this._backupProperties = Object.assign({}, this.properties)
|
||||||
this._backupProperties.tilelayer = Object.assign({}, this.properties.tilelayer)
|
this._backupProperties.tilelayer = Object.assign({}, this.properties.tilelayer)
|
||||||
this._backupProperties.limitBounds = Object.assign({}, this.properties.limitBounds)
|
this._backupProperties.limitBounds = Object.assign({}, this.properties.limitBounds)
|
||||||
this._backupProperties.permissions = Object.assign({}, this.permissions.options)
|
this._backupProperties.permissions = Object.assign({}, this.permissions.properties)
|
||||||
}
|
}
|
||||||
|
|
||||||
resetProperties() {
|
resetProperties() {
|
||||||
this.properties = Object.assign({}, this._backupProperties)
|
this.properties = Object.assign({}, this._backupProperties)
|
||||||
this.properties.tilelayer = Object.assign({}, this._backupProperties.tilelayer)
|
this.properties.tilelayer = Object.assign({}, this._backupProperties.tilelayer)
|
||||||
this.permissions.options = Object.assign({}, this._backupProperties.permissions)
|
this.permissions.properties = Object.assign({}, this._backupProperties.permissions)
|
||||||
}
|
}
|
||||||
|
|
||||||
hasData() {
|
hasData() {
|
||||||
|
@ -994,7 +989,7 @@ export default class Umap extends ServerStored {
|
||||||
],
|
],
|
||||||
]
|
]
|
||||||
const slideshowBuilder = new U.FormBuilder(this, slideshowFields, {
|
const slideshowBuilder = new U.FormBuilder(this, slideshowFields, {
|
||||||
callback: () => this.slideshow.setOptions(this.properties.slideshow),
|
callback: () => this.slideshow.setProperties(this.properties.slideshow),
|
||||||
umap: this,
|
umap: this,
|
||||||
})
|
})
|
||||||
slideshow.appendChild(slideshowBuilder.build())
|
slideshow.appendChild(slideshowBuilder.build())
|
||||||
|
@ -1120,7 +1115,7 @@ export default class Umap extends ServerStored {
|
||||||
this.properties.user = data.user
|
this.properties.user = data.user
|
||||||
if (!this.properties.umap_id) {
|
if (!this.properties.umap_id) {
|
||||||
this.properties.umap_id = data.id
|
this.properties.umap_id = data.id
|
||||||
this.permissions.setOptions(data.permissions)
|
this.permissions.setProperties(data.permissions)
|
||||||
this.permissions.commit()
|
this.permissions.commit()
|
||||||
if (data.permissions?.anonymous_edit_url) {
|
if (data.permissions?.anonymous_edit_url) {
|
||||||
this._leafletMap.once('saved', () => {
|
this._leafletMap.once('saved', () => {
|
||||||
|
@ -1142,7 +1137,7 @@ export default class Umap extends ServerStored {
|
||||||
if (!this.permissions.isDirty) {
|
if (!this.permissions.isDirty) {
|
||||||
// Do not override local changes to permissions,
|
// Do not override local changes to permissions,
|
||||||
// but update in case some other editors changed them in the meantime.
|
// but update in case some other editors changed them in the meantime.
|
||||||
this.permissions.setOptions(data.permissions)
|
this.permissions.setProperties(data.permissions)
|
||||||
this.permissions.commit()
|
this.permissions.commit()
|
||||||
}
|
}
|
||||||
this._leafletMap.once('saved', () => {
|
this._leafletMap.once('saved', () => {
|
||||||
|
@ -1197,7 +1192,7 @@ export default class Umap extends ServerStored {
|
||||||
document.body.classList.add('umap-edit-enabled')
|
document.body.classList.add('umap-edit-enabled')
|
||||||
this.editEnabled = true
|
this.editEnabled = true
|
||||||
this.drop.enable()
|
this.drop.enable()
|
||||||
this._leafletMap.fire('edit:enabled')
|
this.fire('edit:enabled')
|
||||||
this.initSyncEngine()
|
this.initSyncEngine()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1207,13 +1202,17 @@ export default class Umap extends ServerStored {
|
||||||
document.body.classList.remove('umap-edit-enabled')
|
document.body.classList.remove('umap-edit-enabled')
|
||||||
this.editedFeature = null
|
this.editedFeature = null
|
||||||
this.editEnabled = false
|
this.editEnabled = false
|
||||||
this._leafletMap.fire('edit:disabled')
|
this.fire('edit:disabled')
|
||||||
this.editPanel.close()
|
this.editPanel.close()
|
||||||
this.fullPanel.close()
|
this.fullPanel.close()
|
||||||
this.sync.stop()
|
this.sync.stop()
|
||||||
this._leafletMap.closeInplaceToolbar()
|
this._leafletMap.closeInplaceToolbar()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fire(name) {
|
||||||
|
this._leafletMap.fire(name)
|
||||||
|
}
|
||||||
|
|
||||||
askForReset(e) {
|
askForReset(e) {
|
||||||
this.dialog
|
this.dialog
|
||||||
.confirm(translate('Are you sure you want to cancel your changes?'))
|
.confirm(translate('Are you sure you want to cancel your changes?'))
|
||||||
|
@ -1256,12 +1255,14 @@ export default class Umap extends ServerStored {
|
||||||
for (const impact of impacts) {
|
for (const impact of impacts) {
|
||||||
switch (impact) {
|
switch (impact) {
|
||||||
case 'ui':
|
case 'ui':
|
||||||
this._leafletMap.update()
|
this._leafletMap.renderUI()
|
||||||
this.browser.redraw()
|
this.browser.redraw()
|
||||||
this.propagate()
|
this.propagate()
|
||||||
break
|
break
|
||||||
case 'data':
|
case 'data':
|
||||||
this.redrawVisibleDataLayers()
|
this.eachVisibleDataLayer((datalayer) => {
|
||||||
|
datalayer.redraw()
|
||||||
|
})
|
||||||
break
|
break
|
||||||
case 'datalayer-index':
|
case 'datalayer-index':
|
||||||
this.reindexDataLayers()
|
this.reindexDataLayers()
|
||||||
|
@ -1460,7 +1461,7 @@ export default class Umap extends ServerStored {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if (type === 'umap') {
|
if (type === 'umap') {
|
||||||
this.importFromFile(file, 'umap')
|
this.importUmapFile(file, 'umap')
|
||||||
} else {
|
} else {
|
||||||
if (!layer) layer = this.createDataLayer({ name: file.name })
|
if (!layer) layer = this.createDataLayer({ name: file.name })
|
||||||
layer.importFromFile(file, type)
|
layer.importFromFile(file, type)
|
||||||
|
@ -1479,7 +1480,7 @@ export default class Umap extends ServerStored {
|
||||||
|
|
||||||
let mustReindex = false
|
let mustReindex = false
|
||||||
|
|
||||||
for (const option of Object.keys(U.SCHEMA)) {
|
for (const option of Object.keys(SCHEMA)) {
|
||||||
if (typeof importedData.properties[option] !== 'undefined') {
|
if (typeof importedData.properties[option] !== 'undefined') {
|
||||||
this.properties[option] = importedData.properties[option]
|
this.properties[option] = importedData.properties[option]
|
||||||
if (option === 'sortKey') mustReindex = true
|
if (option === 'sortKey') mustReindex = true
|
||||||
|
@ -1499,7 +1500,7 @@ export default class Umap extends ServerStored {
|
||||||
dataLayer.fromUmapGeoJSON(geojson)
|
dataLayer.fromUmapGeoJSON(geojson)
|
||||||
}
|
}
|
||||||
|
|
||||||
this._leafletMap.update()
|
this._leafletMap.renderUI()
|
||||||
this.eachDataLayer((datalayer) => {
|
this.eachDataLayer((datalayer) => {
|
||||||
if (mustReindex) datalayer.reindex()
|
if (mustReindex) datalayer.reindex()
|
||||||
datalayer.redraw()
|
datalayer.redraw()
|
||||||
|
@ -1509,7 +1510,7 @@ export default class Umap extends ServerStored {
|
||||||
this.isDirty = true
|
this.isDirty = true
|
||||||
}
|
}
|
||||||
|
|
||||||
importFromFile(file) {
|
importUmapFile(file) {
|
||||||
const reader = new FileReader()
|
const reader = new FileReader()
|
||||||
reader.readAsText(file)
|
reader.readAsText(file)
|
||||||
reader.onload = (e) => {
|
reader.onload = (e) => {
|
||||||
|
|
|
@ -25,6 +25,16 @@ export function checkId(string) {
|
||||||
return /^[A-Za-z0-9]{5}$/.test(string)
|
return /^[A-Za-z0-9]{5}$/.test(string)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function _getPropertyName(field) {
|
||||||
|
const filtered_field = ['options.', 'properties.'].reduce(
|
||||||
|
(acc, prefix) => acc.replace(prefix, ''),
|
||||||
|
field
|
||||||
|
)
|
||||||
|
return filtered_field.split('.')[0]
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Compute the impacts for a given list of fields.
|
* Compute the impacts for a given list of fields.
|
||||||
*
|
*
|
||||||
|
@ -41,7 +51,7 @@ export function getImpactsFromSchema(fields, schema) {
|
||||||
// remove the option prefix for fields
|
// remove the option prefix for fields
|
||||||
// And only keep the first part in case of a subfield
|
// And only keep the first part in case of a subfield
|
||||||
// (e.g "options.limitBounds.foobar" will just return "limitBounds")
|
// (e.g "options.limitBounds.foobar" will just return "limitBounds")
|
||||||
return field.replace('options.', '').replace('properties.', '').split('.')[0]
|
return _getPropertyName(field)
|
||||||
})
|
})
|
||||||
.reduce((acc, field) => {
|
.reduce((acc, field) => {
|
||||||
// retrieve the "impacts" field from the schema
|
// retrieve the "impacts" field from the schema
|
||||||
|
@ -66,10 +76,7 @@ export function getImpactsFromSchema(fields, schema) {
|
||||||
export function fieldInSchema(field, schema) {
|
export function fieldInSchema(field, schema) {
|
||||||
const current_schema = schema || U.SCHEMA
|
const current_schema = schema || U.SCHEMA
|
||||||
if (typeof field !== 'string') return false
|
if (typeof field !== 'string') return false
|
||||||
const field_name = field
|
const field_name = _getPropertyName(field)
|
||||||
.replace('options.', '')
|
|
||||||
.replace('properties.', '')
|
|
||||||
.split('.')[0]
|
|
||||||
return current_schema[field_name] !== undefined
|
return current_schema[field_name] !== undefined
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@ U.BaseAction = L.ToolbarAction.extend({
|
||||||
initialize: function (map) {
|
initialize: function (map) {
|
||||||
this.map = map
|
this.map = map
|
||||||
if (this.options.label) {
|
if (this.options.label) {
|
||||||
this.options.tooltip = this.map.umap.help.displayLabel(
|
this.options.tooltip = this.map._umap.help.displayLabel(
|
||||||
this.options.label,
|
this.options.label,
|
||||||
(withKbdTag = false)
|
(withKbdTag = false)
|
||||||
)
|
)
|
||||||
|
@ -25,7 +25,7 @@ U.ImportAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.importer.open()
|
this.map._umap.importer.open()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -37,7 +37,7 @@ U.EditLayersAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.editDatalayers()
|
this.map._umap.editDatalayers()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -49,7 +49,7 @@ U.EditCaptionAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.editCaption()
|
this.map._umap.editCaption()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -61,7 +61,7 @@ U.EditPropertiesAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.edit()
|
this.map._umap.edit()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -84,7 +84,7 @@ U.UpdateExtentAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.setCenterAndZoom()
|
this.map._umap.setCenterAndZoom()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -95,7 +95,7 @@ U.UpdatePermsAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.umap.permissions.edit()
|
this.map._umap.permissions.edit()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -107,7 +107,7 @@ U.DrawMarkerAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.startMarker()
|
this.map.editTools.startMarker()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -119,7 +119,7 @@ U.DrawPolylineAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.startPolyline()
|
this.map.editTools.startPolyline()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -131,7 +131,7 @@ U.DrawPolygonAction = U.BaseAction.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
this.map.startPolygon()
|
this.map.editTools.startPolygon()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -143,7 +143,7 @@ U.AddPolylineShapeAction = U.BaseAction.extend({
|
||||||
|
|
||||||
addHooks: function () {
|
addHooks: function () {
|
||||||
// FIXME: smells bad
|
// FIXME: smells bad
|
||||||
this.map.umap.editedFeature.ui.editor.newShape()
|
this.map._umap.editedFeature.ui.editor.newShape()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -306,23 +306,23 @@ U.DrawToolbar = L.Toolbar.Control.extend({
|
||||||
|
|
||||||
appendToContainer: function (container) {
|
appendToContainer: function (container) {
|
||||||
this.options.actions = []
|
this.options.actions = []
|
||||||
if (this.map.umap.properties.enableMarkerDraw) {
|
if (this.map._umap.properties.enableMarkerDraw) {
|
||||||
this.options.actions.push(U.DrawMarkerAction)
|
this.options.actions.push(U.DrawMarkerAction)
|
||||||
}
|
}
|
||||||
if (this.map.umap.properties.enablePolylineDraw) {
|
if (this.map._umap.properties.enablePolylineDraw) {
|
||||||
this.options.actions.push(U.DrawPolylineAction)
|
this.options.actions.push(U.DrawPolylineAction)
|
||||||
if (
|
if (
|
||||||
this.map.umap.editedFeature &&
|
this.map._umap.editedFeature &&
|
||||||
this.map.umap.editedFeature instanceof U.LineString
|
this.map._umap.editedFeature instanceof U.LineString
|
||||||
) {
|
) {
|
||||||
this.options.actions.push(U.AddPolylineShapeAction)
|
this.options.actions.push(U.AddPolylineShapeAction)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (this.map.umap.properties.enablePolygonDraw) {
|
if (this.map._umap.properties.enablePolygonDraw) {
|
||||||
this.options.actions.push(U.DrawPolygonAction)
|
this.options.actions.push(U.DrawPolygonAction)
|
||||||
if (
|
if (
|
||||||
this.map.umap.editedFeature &&
|
this.map._umap.editedFeature &&
|
||||||
this.map.umap.editedFeature instanceof U.Polygon
|
this.map._umap.editedFeature instanceof U.Polygon
|
||||||
) {
|
) {
|
||||||
this.options.actions.push(U.AddPolygonShapeAction)
|
this.options.actions.push(U.AddPolygonShapeAction)
|
||||||
}
|
}
|
||||||
|
@ -372,9 +372,9 @@ U.DropControl = L.Class.extend({
|
||||||
this.dropzone.classList.remove('umap-dragover')
|
this.dropzone.classList.remove('umap-dragover')
|
||||||
L.DomEvent.stop(e)
|
L.DomEvent.stop(e)
|
||||||
for (const file of event.dataTransfer.files) {
|
for (const file of event.dataTransfer.files) {
|
||||||
this.map.umap.processFileToImport(file)
|
this.map._umap.processFileToImport(file)
|
||||||
}
|
}
|
||||||
this.map.umap.onceDataLoaded(this.map.umap.fitDataBounds)
|
this.map._umap.onceDataLoaded(this.map._umap.fitDataBounds)
|
||||||
},
|
},
|
||||||
|
|
||||||
dragleave: function () {
|
dragleave: function () {
|
||||||
|
@ -394,15 +394,15 @@ U.EditControl = L.Control.extend({
|
||||||
'',
|
'',
|
||||||
container,
|
container,
|
||||||
L._('Edit'),
|
L._('Edit'),
|
||||||
map.umap.enableEdit,
|
map._umap.enableEdit,
|
||||||
map.umap
|
map._umap
|
||||||
)
|
)
|
||||||
L.DomEvent.on(
|
L.DomEvent.on(
|
||||||
enableEditing,
|
enableEditing,
|
||||||
'mouseover',
|
'mouseover',
|
||||||
() => {
|
() => {
|
||||||
map.umap.tooltip.open({
|
map._umap.tooltip.open({
|
||||||
content: map.umap.help.displayLabel('TOGGLE_EDIT'),
|
content: map._umap.help.displayLabel('TOGGLE_EDIT'),
|
||||||
anchor: enableEditing,
|
anchor: enableEditing,
|
||||||
position: 'bottom',
|
position: 'bottom',
|
||||||
delay: 750,
|
delay: 750,
|
||||||
|
@ -484,7 +484,7 @@ U.PermanentCreditsControl = L.Control.extend({
|
||||||
|
|
||||||
L.Control.Button = L.Control.extend({
|
L.Control.Button = L.Control.extend({
|
||||||
initialize: function (umap, options) {
|
initialize: function (umap, options) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
L.Control.prototype.initialize.call(this, options)
|
L.Control.prototype.initialize.call(this, options)
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -517,11 +517,11 @@ U.DataLayersControl = L.Control.Button.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
afterAdd: function (container) {
|
afterAdd: function (container) {
|
||||||
U.Utils.toggleBadge(container, this.umap.browser?.hasFilters())
|
U.Utils.toggleBadge(container, this._umap.browser?.hasFilters())
|
||||||
},
|
},
|
||||||
|
|
||||||
onClick: function () {
|
onClick: function () {
|
||||||
this.umap.openBrowser()
|
this._umap.openBrowser()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -533,7 +533,7 @@ U.CaptionControl = L.Control.Button.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
onClick: function () {
|
onClick: function () {
|
||||||
this.umap.openCaption()
|
this._umap.openCaption()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -544,13 +544,12 @@ U.StarControl = L.Control.Button.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
getClassName: function () {
|
getClassName: function () {
|
||||||
const status = this.umap.properties.starred ? ' starred' : ''
|
const status = this._umap.properties.starred ? ' starred' : ''
|
||||||
return `leaflet-control-star umap-control${status}`
|
return `leaflet-control-star umap-control${status}`
|
||||||
},
|
},
|
||||||
|
|
||||||
onClick: function () {
|
onClick: function () {
|
||||||
console.log(this.umap)
|
this._umap.star()
|
||||||
this.umap.star()
|
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -562,7 +561,7 @@ L.Control.Embed = L.Control.Button.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
onClick: function () {
|
onClick: function () {
|
||||||
this.umap.share.open()
|
this._umap.share.open()
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -655,7 +654,7 @@ U.TileLayerChooser = L.Control.extend({
|
||||||
L.DomUtil.createTitle(container, L._('Change tilelayers'), 'icon-tilelayer')
|
L.DomUtil.createTitle(container, L._('Change tilelayers'), 'icon-tilelayer')
|
||||||
this._tilelayers_container = L.DomUtil.create('ul', '', container)
|
this._tilelayers_container = L.DomUtil.create('ul', '', container)
|
||||||
this.buildList(options)
|
this.buildList(options)
|
||||||
const panel = options.edit ? this.map.umap.editPanel : this.map.umap.panel
|
const panel = options.edit ? this.map._umap.editPanel : this.map._umap.panel
|
||||||
panel.open({ content: container })
|
panel.open({ content: container })
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -708,8 +707,8 @@ U.AttributionControl = L.Control.Attribution.extend({
|
||||||
this._container.innerHTML = ''
|
this._container.innerHTML = ''
|
||||||
const container = L.DomUtil.create('div', 'attribution-container', this._container)
|
const container = L.DomUtil.create('div', 'attribution-container', this._container)
|
||||||
container.innerHTML = credits
|
container.innerHTML = credits
|
||||||
const shortCredit = this._map.umap.getOption('shortCredit')
|
const shortCredit = this._map._umap.getProperty('shortCredit')
|
||||||
const captionMenus = this._map.umap.getOption('captionMenus')
|
const captionMenus = this._map._umap.getProperty('captionMenus')
|
||||||
if (shortCredit) {
|
if (shortCredit) {
|
||||||
L.DomUtil.element({
|
L.DomUtil.element({
|
||||||
tagName: 'span',
|
tagName: 'span',
|
||||||
|
@ -720,7 +719,7 @@ U.AttributionControl = L.Control.Attribution.extend({
|
||||||
if (captionMenus) {
|
if (captionMenus) {
|
||||||
const link = L.DomUtil.add('a', '', container, ` — ${L._('Open caption')}`)
|
const link = L.DomUtil.add('a', '', container, ` — ${L._('Open caption')}`)
|
||||||
L.DomEvent.on(link, 'click', L.DomEvent.stop)
|
L.DomEvent.on(link, 'click', L.DomEvent.stop)
|
||||||
.on(link, 'click', () => this._map.umap.openCaption())
|
.on(link, 'click', () => this._map._umap.openCaption())
|
||||||
.on(link, 'dblclick', L.DomEvent.stop)
|
.on(link, 'dblclick', L.DomEvent.stop)
|
||||||
}
|
}
|
||||||
if (window.top === window.self && captionMenus) {
|
if (window.top === window.self && captionMenus) {
|
||||||
|
@ -912,7 +911,7 @@ U.SearchControl = L.Control.extend({
|
||||||
this.map.fire('dataload', { id: id })
|
this.map.fire('dataload', { id: id })
|
||||||
})
|
})
|
||||||
this.search.resultsContainer = resultsContainer
|
this.search.resultsContainer = resultsContainer
|
||||||
this.map.umap.panel.open({ content: container }).then(input.focus())
|
this.map._umap.panel.open({ content: container }).then(input.focus())
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -953,7 +952,7 @@ L.Control.Loading.include({
|
||||||
|
|
||||||
U.Editable = L.Editable.extend({
|
U.Editable = L.Editable.extend({
|
||||||
initialize: function (umap, options) {
|
initialize: function (umap, options) {
|
||||||
this.umap = umap
|
this._umap = umap
|
||||||
L.Editable.prototype.initialize.call(this, umap._leafletMap, options)
|
L.Editable.prototype.initialize.call(this, umap._leafletMap, options)
|
||||||
this.on('editable:drawing:click editable:drawing:move', this.drawingTooltip)
|
this.on('editable:drawing:click editable:drawing:move', this.drawingTooltip)
|
||||||
// Layer for items added by users
|
// Layer for items added by users
|
||||||
|
@ -962,7 +961,7 @@ U.Editable = L.Editable.extend({
|
||||||
})
|
})
|
||||||
this.on('editable:drawing:commit', function (event) {
|
this.on('editable:drawing:commit', function (event) {
|
||||||
event.layer.feature.isDirty = true
|
event.layer.feature.isDirty = true
|
||||||
if (this.umap.editedFeature !== event.layer) event.layer.feature.edit(event)
|
if (this._umap.editedFeature !== event.layer) event.layer.feature.edit(event)
|
||||||
})
|
})
|
||||||
this.on('editable:editing', (event) => {
|
this.on('editable:editing', (event) => {
|
||||||
const feature = event.layer.feature
|
const feature = event.layer.feature
|
||||||
|
@ -984,24 +983,24 @@ U.Editable = L.Editable.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
createPolyline: function (latlngs) {
|
createPolyline: function (latlngs) {
|
||||||
const datalayer = this.umap.defaultEditDataLayer()
|
const datalayer = this._umap.defaultEditDataLayer()
|
||||||
const point = new U.LineString(datalayer, {
|
const point = new U.LineString(this._umap, datalayer, {
|
||||||
geometry: { type: 'LineString', coordinates: [] },
|
geometry: { type: 'LineString', coordinates: [] },
|
||||||
})
|
})
|
||||||
return point.ui
|
return point.ui
|
||||||
},
|
},
|
||||||
|
|
||||||
createPolygon: function (latlngs) {
|
createPolygon: function (latlngs) {
|
||||||
const datalayer = this.umap.defaultEditDataLayer()
|
const datalayer = this._umap.defaultEditDataLayer()
|
||||||
const point = new U.Polygon(datalayer, {
|
const point = new U.Polygon(this._umap, datalayer, {
|
||||||
geometry: { type: 'Polygon', coordinates: [] },
|
geometry: { type: 'Polygon', coordinates: [] },
|
||||||
})
|
})
|
||||||
return point.ui
|
return point.ui
|
||||||
},
|
},
|
||||||
|
|
||||||
createMarker: function (latlng) {
|
createMarker: function (latlng) {
|
||||||
const datalayer = this.umap.defaultEditDataLayer()
|
const datalayer = this._umap.defaultEditDataLayer()
|
||||||
const point = new U.Point(datalayer, {
|
const point = new U.Point(this._umap, datalayer, {
|
||||||
geometry: { type: 'Point', coordinates: [latlng.lng, latlng.lat] },
|
geometry: { type: 'Point', coordinates: [latlng.lng, latlng.lat] },
|
||||||
})
|
})
|
||||||
return point.ui
|
return point.ui
|
||||||
|
@ -1009,15 +1008,15 @@ U.Editable = L.Editable.extend({
|
||||||
|
|
||||||
_getDefaultProperties: function () {
|
_getDefaultProperties: function () {
|
||||||
const result = {}
|
const result = {}
|
||||||
if (this.umap.properties.featuresHaveOwner?.user) {
|
if (this._umap.properties.featuresHaveOwner?.user) {
|
||||||
result.geojson = { properties: { owner: this.umap.properties.user.id } }
|
result.geojson = { properties: { owner: this._umap.properties.user.id } }
|
||||||
}
|
}
|
||||||
return result
|
return result
|
||||||
},
|
},
|
||||||
|
|
||||||
connectCreatedToMap: function (layer) {
|
connectCreatedToMap: function (layer) {
|
||||||
// Overrided from Leaflet.Editable
|
// Overrided from Leaflet.Editable
|
||||||
const datalayer = this.umap.defaultEditDataLayer()
|
const datalayer = this._umap.defaultEditDataLayer()
|
||||||
datalayer.addFeature(layer.feature)
|
datalayer.addFeature(layer.feature)
|
||||||
layer.isDirty = true
|
layer.isDirty = true
|
||||||
return layer
|
return layer
|
||||||
|
@ -1025,7 +1024,7 @@ U.Editable = L.Editable.extend({
|
||||||
|
|
||||||
drawingTooltip: function (e) {
|
drawingTooltip: function (e) {
|
||||||
if (e.layer instanceof L.Marker && e.type === 'editable:drawing:start') {
|
if (e.layer instanceof L.Marker && e.type === 'editable:drawing:start') {
|
||||||
this.umap.tooltip.open({ content: L._('Click to add a marker') })
|
this._umap.tooltip.open({ content: L._('Click to add a marker') })
|
||||||
}
|
}
|
||||||
if (!(e.layer instanceof L.Polyline)) {
|
if (!(e.layer instanceof L.Polyline)) {
|
||||||
// only continue with Polylines and Polygons
|
// only continue with Polylines and Polygons
|
||||||
|
@ -1072,12 +1071,12 @@ U.Editable = L.Editable.extend({
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (content) {
|
if (content) {
|
||||||
this.umap.tooltip.open({ content: content })
|
this._umap.tooltip.open({ content: content })
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
closeTooltip: function () {
|
closeTooltip: function () {
|
||||||
this.umap.closeTooltip()
|
this._umap.closeTooltip()
|
||||||
},
|
},
|
||||||
|
|
||||||
onVertexRawClick: (e) => {
|
onVertexRawClick: (e) => {
|
||||||
|
@ -1088,7 +1087,7 @@ U.Editable = L.Editable.extend({
|
||||||
|
|
||||||
onEscape: function () {
|
onEscape: function () {
|
||||||
this.once('editable:drawing:end', (event) => {
|
this.once('editable:drawing:end', (event) => {
|
||||||
this.umap.tooltip.close()
|
this._umap.tooltip.close()
|
||||||
// Leaflet.Editable will delete the drawn shape if invalid
|
// Leaflet.Editable will delete the drawn shape if invalid
|
||||||
// (eg. line has only one drawn point)
|
// (eg. line has only one drawn point)
|
||||||
// So let's check if the layer has no more shape
|
// So let's check if the layer has no more shape
|
||||||
|
|
|
@ -221,21 +221,16 @@ L.FormBuilder.Element.include({
|
||||||
this.label = L.DomUtil.create('label', '', this.getLabelParent())
|
this.label = L.DomUtil.create('label', '', this.getLabelParent())
|
||||||
this.label.textContent = this.label.title = this.options.label
|
this.label.textContent = this.label.title = this.options.label
|
||||||
if (this.options.helpEntries) {
|
if (this.options.helpEntries) {
|
||||||
this.builder.umap.help.button(this.label, this.options.helpEntries)
|
this.builder._umap.help.button(this.label, this.options.helpEntries)
|
||||||
} else if (this.options.helpTooltip) {
|
} else if (this.options.helpTooltip) {
|
||||||
const info = L.DomUtil.create('i', 'info', this.label)
|
const info = L.DomUtil.create('i', 'info', this.label)
|
||||||
L.DomEvent.on(
|
L.DomEvent.on(info, 'mouseover', () => {
|
||||||
info,
|
this.builder._umap.tooltip.open({
|
||||||
'mouseover',
|
anchor: info,
|
||||||
function () {
|
content: this.options.helpTooltip,
|
||||||
this.builder.umap.tooltip.open({
|
position: 'top',
|
||||||
anchor: info,
|
})
|
||||||
content: this.options.helpTooltip,
|
})
|
||||||
position: 'top',
|
|
||||||
})
|
|
||||||
},
|
|
||||||
this
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -359,7 +354,7 @@ L.FormBuilder.SlideshowDelay = L.FormBuilder.IntSelect.extend({
|
||||||
L.FormBuilder.DataLayerSwitcher = L.FormBuilder.Select.extend({
|
L.FormBuilder.DataLayerSwitcher = L.FormBuilder.Select.extend({
|
||||||
getOptions: function () {
|
getOptions: function () {
|
||||||
const options = []
|
const options = []
|
||||||
this.builder.umap.eachDataLayerReverse((datalayer) => {
|
this.builder._umap.eachDataLayerReverse((datalayer) => {
|
||||||
if (
|
if (
|
||||||
datalayer.isLoaded() &&
|
datalayer.isLoaded() &&
|
||||||
!datalayer.isDataReadOnly() &&
|
!datalayer.isDataReadOnly() &&
|
||||||
|
@ -376,11 +371,11 @@ L.FormBuilder.DataLayerSwitcher = L.FormBuilder.Select.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
toJS: function () {
|
toJS: function () {
|
||||||
return this.builder.umap.datalayers[this.value()]
|
return this.builder._umap.datalayers[this.value()]
|
||||||
},
|
},
|
||||||
|
|
||||||
set: function () {
|
set: function () {
|
||||||
this.builder.umap.lastUsedDataLayer = this.toJS()
|
this.builder._umap.lastUsedDataLayer = this.toJS()
|
||||||
this.obj.changeDataLayer(this.toJS())
|
this.obj.changeDataLayer(this.toJS())
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
@ -469,8 +464,8 @@ L.FormBuilder.IconUrl = L.FormBuilder.BlurInput.extend({
|
||||||
onDefine: async function () {
|
onDefine: async function () {
|
||||||
this.buttons.innerHTML = ''
|
this.buttons.innerHTML = ''
|
||||||
this.footer.innerHTML = ''
|
this.footer.innerHTML = ''
|
||||||
const [{ pictogram_list }, response, error] = await this.builder.umap.server.get(
|
const [{ pictogram_list }, response, error] = await this.builder._umap.server.get(
|
||||||
this.builder.umap.properties.urls.pictogram_list_json
|
this.builder._umap.properties.urls.pictogram_list_json
|
||||||
)
|
)
|
||||||
if (!error) this.pictogram_list = pictogram_list
|
if (!error) this.pictogram_list = pictogram_list
|
||||||
this.buildTabs()
|
this.buildTabs()
|
||||||
|
@ -1168,7 +1163,7 @@ U.FormBuilder = L.FormBuilder.extend({
|
||||||
},
|
},
|
||||||
|
|
||||||
initialize: function (obj, fields, options = {}) {
|
initialize: function (obj, fields, options = {}) {
|
||||||
this.umap = obj.umap || options.umap
|
this._umap = obj._umap || options.umap
|
||||||
this.computeDefaultOptions()
|
this.computeDefaultOptions()
|
||||||
L.FormBuilder.prototype.initialize.call(this, obj, fields, options)
|
L.FormBuilder.prototype.initialize.call(this, obj, fields, options)
|
||||||
this.on('finish', this.finish)
|
this.on('finish', this.finish)
|
||||||
|
|
Loading…
Reference in a new issue