Subversion Repositories eFlore/Applications.cel

Rev

Rev 3870 | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 3870 Rev 3954
1
import {NOMINATIM_OSM_URL,TbPlaces} from "./modules/Locality.js";
1
import {NOMINATIM_OSM_URL,TbPlaces} from "./modules/Locality.js";
2
 
2
 
3
const tileLayers = {
3
const tileLayers = {
4
    googleHybrid: [
4
    googleHybrid: [
5
        'https://{s}.google.com/vt/lyrs=s,h&x={x}&y={y}&z={z}',
5
        'https://{s}.google.com/vt/lyrs=s,h&x={x}&y={y}&z={z}',
6
        {
6
        {
7
            attribution: '<a href="https://www.google.com" target="_blank">\xa9 Google Maps</a>',
7
            attribution: '<a href="https://www.google.com" target="_blank">\xa9 Google Maps</a>',
8
            subdomains: ["mt0","mt1","mt2","mt3"],
8
            subdomains: ["mt0","mt1","mt2","mt3"],
9
            maxZoom: 20
9
            maxZoom: 20
10
        }
10
        }
11
    ],
11
    ],
12
    osm: [
12
    osm: [
13
        'https://osm.tela-botanica.org/tuiles/osmfr/{z}/{x}/{y}.png',
13
        'https://b.tile.openstreetmap.fr/osmfr/{z}/{x}/{y}.png',
14
        {
14
        {
15
            attribution: 'Data © <a href="http://osm.org/copyright">OpenStreetMap</a>',
15
            attribution: 'Data © <a href="http://osm.org/copyright">OpenStreetMap</a>',
16
            maxZoom: 18
16
            maxZoom: 18
17
        }
17
        }
18
    ]
18
    ]
19
};
19
};
20
const defaultPosition = {
20
const defaultPosition = {
21
    lat: 47.0504,
21
    lat: 47.0504,
22
    lng: 2.2347
22
    lng: 2.2347
23
};
23
};
24
const defaultCityZoom = 12;
24
const defaultCityZoom = 12;
25
const defaultZoom = 4;
25
const defaultZoom = 4;
26
const geometryFilterDefault = 'point';
26
const geometryFilterDefault = 'point';
27
const defaultMapIdAttr = 'tb-geolocation';
27
const defaultMapIdAttr = 'tb-geolocation';
28
const markerImgBaseUrl = URL_BASE +'js/tb-geoloc/img/';
28
const markerImgBaseUrl = URL_BASE +'js/tb-geoloc/img/';
29
const markerIcon = L.Icon.extend({
29
const markerIcon = L.Icon.extend({
30
    options: {
30
    options: {
31
        shadowUrl: markerImgBaseUrl +'marker-shadow.png',
31
        shadowUrl: markerImgBaseUrl +'marker-shadow.png',
32
        iconAnchor: new L.Point(12, 40),//correctly replaces the dot of the pointer
32
        iconAnchor: new L.Point(12, 40),//correctly replaces the dot of the pointer
33
        iconSize: new L.Point(24,40),
33
        iconSize: new L.Point(24,40),
34
        iconUrl: markerImgBaseUrl +'marker-icon.png',
34
        iconUrl: markerImgBaseUrl +'marker-icon.png',
35
    }
35
    }
36
});
36
});
37
const defaultPolylineOptions = {
37
const defaultPolylineOptions = {
38
    shapeOptions: {
38
    shapeOptions: {
39
        weight: 5
39
        weight: 5
40
    },
40
    },
41
    showLength: true,
41
    showLength: true,
42
    repeatMode: false
42
    repeatMode: false
43
};
43
};
44
 
44
 
45
const drawLocale = {
45
const drawLocale = {
46
    edit: {
46
    edit: {
47
        handlers: {
47
        handlers: {
48
            edit: {
48
            edit: {
49
                tooltip: {
49
                tooltip: {
50
                    subtext: 'Cliquer sur annuler pour supprimer les changements',
50
                    subtext: 'Cliquer sur annuler pour supprimer les changements',
51
                    text: 'Déplacez les marqueurs pour modifier leur position'
51
                    text: 'Déplacez les marqueurs pour modifier leur position'
52
                }
52
                }
53
            },
53
            },
54
            remove: {
54
            remove: {
55
                tooltip: {
55
                tooltip: {
56
                    text: 'cliquer sur une ligne pour supprimer'
56
                    text: 'cliquer sur une ligne pour supprimer'
57
                }
57
                }
58
            }
58
            }
59
        },
59
        },
60
        toolbar: {
60
        toolbar: {
61
            actions: {
61
            actions: {
62
                cancel: {
62
                cancel: {
63
                    text: 'Annuler',
63
                    text: 'Annuler',
64
                    title: 'Annuler'
64
                    title: 'Annuler'
65
                },
65
                },
66
                clearAll: {
66
                clearAll: {
67
                    text: 'Effacer',
67
                    text: 'Effacer',
68
                    title: 'Tout effacer'
68
                    title: 'Tout effacer'
69
                },
69
                },
70
                save: {
70
                save: {
71
                    text: 'Sauvegarder',
71
                    text: 'Sauvegarder',
72
                    title: 'Sauvegarder les changements'
72
                    title: 'Sauvegarder les changements'
73
                }
73
                }
74
            },
74
            },
75
            buttons: {
75
            buttons: {
76
                edit: 'Editer',
76
                edit: 'Editer',
77
                editDisabled: 'Rien à editer',
77
                editDisabled: 'Rien à editer',
78
                remove: 'Supprimer',
78
                remove: 'Supprimer',
79
                removeDisabled: 'Rien à supprimer'
79
                removeDisabled: 'Rien à supprimer'
80
            }
80
            }
81
        }
81
        }
82
    },
82
    },
83
    draw : {
83
    draw : {
84
        toolbar: {
84
        toolbar: {
85
            actions: {
85
            actions: {
86
                text: 'Annuler',
86
                text: 'Annuler',
87
                title: 'Annuler'
87
                title: 'Annuler'
88
            },
88
            },
89
            buttons: {
89
            buttons: {
90
                polyline: 'Dessiner une ligne',
90
                polyline: 'Dessiner une ligne',
91
                marker: 'Pointer une position'
91
                marker: 'Pointer une position'
92
            },
92
            },
93
            finish: {
93
            finish: {
94
                text: 'Terminer',
94
                text: 'Terminer',
95
                title: 'Terminer'
95
                title: 'Terminer'
96
            },
96
            },
97
            undo: {
97
            undo: {
98
                text: 'Supprimer',
98
                text: 'Supprimer',
99
                title: 'Supprimer le dernier point'
99
                title: 'Supprimer le dernier point'
100
            }
100
            }
101
        },
101
        },
102
        handlers: {
102
        handlers: {
103
            polyline: {
103
            polyline: {
104
                tooltip: {
104
                tooltip: {
105
                    start: 'Cliquer sur la carte pour placer le début de la ligne',
105
                    start: 'Cliquer sur la carte pour placer le début de la ligne',
106
                    cont: 'Positionner le prochain point et cliquer',
106
                    cont: 'Positionner le prochain point et cliquer',
107
                    end: 'Re-cliquer sur le dernier point pour finir la ligne'
107
                    end: 'Re-cliquer sur le dernier point pour finir la ligne'
108
                }
108
                }
109
            },
109
            },
110
            marker: {
110
            marker: {
111
                tooltip: {
111
                tooltip: {
112
                    start: 'Cliquer sur la carte pour placer le marqueur'
112
                    start: 'Cliquer sur la carte pour placer le marqueur'
113
                }
113
                }
114
            },
114
            },
115
            rectangle: {tooltip: {}},
115
            rectangle: {tooltip: {}},
116
            simpleshape: {tooltip: {}},
116
            simpleshape: {tooltip: {}},
117
            circle: {tooltip: {}},
117
            circle: {tooltip: {}},
118
            circlemarker: {tooltip: {}}
118
            circlemarker: {tooltip: {}}
119
        }
119
        }
120
    }
120
    }
121
};
121
};
122
 
122
 
123
/***************************************************/
123
/***************************************************/
124
 
124
 
125
export function Geoloc() {
125
export function Geoloc() {
126
    this.map = {};
126
    this.map = {};
127
    this.coordinates = defaultPosition;
127
    this.coordinates = defaultPosition;
128
    this.geojson = {};
128
    this.geojson = {};
129
    this.editableLayers = {};
129
    this.editableLayers = {};
130
    this.defaultDrawControlOptions = {};
130
    this.defaultDrawControlOptions = {};
131
    this.drawControl = {};
131
    this.drawControl = {};
132
    this.defaultEditOptions = false;
132
    this.defaultEditOptions = false;
133
    this.layer = {};
133
    this.layer = {};
134
};
134
};
135
 
135
 
136
Geoloc.prototype.init = function(suffix = '') {
136
Geoloc.prototype.init = function(suffix = '') {
137
    this.mapIdAttr = defaultMapIdAttr + suffix;
137
    this.mapIdAttr = defaultMapIdAttr + suffix;
138
    this.geolocLabel = document.getElementById('geoloc-label' + suffix);
138
    this.geolocLabel = document.getElementById('geoloc-label' + suffix);
139
    this.initForm();
139
    this.initForm();
140
    this.initEvts();
140
    this.initEvts();
141
};
141
};
142
 
142
 
143
Geoloc.prototype.initForm = function() {
143
Geoloc.prototype.initForm = function() {
144
    this.mapEl = document.getElementById(this.mapIdAttr);
144
    this.mapEl = document.getElementById(this.mapIdAttr);
145
    this.zoom = this.mapEl.dataset.zoom || defaultZoom;
145
    this.zoom = this.mapEl.dataset.zoom || defaultZoom;
146
    this.geometryFilter = this.mapEl.dataset.typeLocalisation || geometryFilterDefault;
146
    this.geometryFilter = this.mapEl.dataset.typeLocalisation || geometryFilterDefault;
147
 
147
 
148
    const formSuffix = this.mapEl.dataset.formSuffix;
148
    const formSuffix = this.mapEl.dataset.formSuffix;
149
 
149
 
150
    this.latitudeEl = document.getElementById('latitude' + formSuffix);
150
    this.latitudeEl = document.getElementById('latitude' + formSuffix);
151
    this.longitudeEl = document.getElementById('longitude' + formSuffix);
151
    this.longitudeEl = document.getElementById('longitude' + formSuffix);
152
};
152
};
153
 
153
 
154
Geoloc.prototype.initEvts = function() {
154
Geoloc.prototype.initEvts = function() {
155
    this.initMap();
155
    this.initMap();
156
    this.initMapCoordinates();
156
    this.initMapCoordinates();
157
    this.initSearchLocality();
157
    this.initSearchLocality();
158
};
158
};
159
 
159
 
160
Geoloc.prototype.initMap = function() {
160
Geoloc.prototype.initMap = function() {
161
    this.map = this.createLocationMap();
161
    this.map = this.createLocationMap();
162
 
162
 
163
    // interactions with map
163
    // interactions with map
164
    this.map.on(L.Draw.Event.CREATED, evt => {
164
    this.map.on(L.Draw.Event.CREATED, evt => {
165
        this.layer = evt.layer;
165
        this.layer = evt.layer;
166
 
166
 
167
        // created marker or polyline with drawControl
167
        // created marker or polyline with drawControl
168
        // no more need this drawcontrol: remove
168
        // no more need this drawcontrol: remove
169
        // (polyline: another one will be added with only edit toolbar)
169
        // (polyline: another one will be added with only edit toolbar)
170
        this.map.removeControl(this.drawControl);
170
        this.map.removeControl(this.drawControl);
171
 
171
 
172
        if ('marker' === evt.layerType) {
172
        if ('marker' === evt.layerType) {
173
            this.onMarkerCreated();
173
            this.onMarkerCreated();
174
        } else if ('polyline' === evt.layerType) {
174
        } else if ('polyline' === evt.layerType) {
175
            this.handlePolylineEvents();
175
            this.handlePolylineEvents();
176
        }
176
        }
177
    });
177
    });
178
 
178
 
179
    this.map.on(L.Draw.Event.EDITED, evt => {
179
    this.map.on(L.Draw.Event.EDITED, evt => {
180
        const layers = evt.layers;
180
        const layers = evt.layers;
181
 
181
 
182
        this.map.removeLayer(this.layer);
182
        this.map.removeLayer(this.layer);
183
 
183
 
184
        layers.eachLayer(layer => {
184
        layers.eachLayer(layer => {
185
            this.layer = layer;
185
            this.layer = layer;
186
            this.handlePolylineEvents(false);
186
            this.handlePolylineEvents(false);
187
        });
187
        });
188
    });
188
    });
189
 
189
 
190
    this.map.on(L.Draw.Event.DELETED, evt => {
190
    this.map.on(L.Draw.Event.DELETED, evt => {
191
        this.reSetDrawControl();
191
        this.reSetDrawControl();
192
    });
192
    });
193
};
193
};
194
 
194
 
195
Geoloc.prototype.initMapCoordinates = function() {
195
Geoloc.prototype.initMapCoordinates = function() {
196
    if (!!this.latitudeEl.value && !!this.longitudeEl.value) {
196
    if (!!this.latitudeEl.value && !!this.longitudeEl.value) {
197
        this.setMapCoordinates({
197
        this.setMapCoordinates({
198
            'lat': this.latitudeEl.value,
198
            'lat': this.latitudeEl.value,
199
            'lng': this.longitudeEl.value
199
            'lng': this.longitudeEl.value
200
        });
200
        });
201
    }
201
    }
202
    this.onCoordinates();
202
    this.onCoordinates();
203
};
203
};
204
 
204
 
205
Geoloc.prototype.reSetDrawControl = function() {
205
Geoloc.prototype.reSetDrawControl = function() {
206
    this.map.removeLayer(this.layer);
206
    this.map.removeLayer(this.layer);
207
    this.map.removeControl(this.drawControl);
207
    this.map.removeControl(this.drawControl);
208
    this.setDrawControl(this.map);
208
    this.setDrawControl(this.map);
209
};
209
};
210
 
210
 
211
Geoloc.prototype.createLocationMap = function() {
211
Geoloc.prototype.createLocationMap = function() {
212
    const lthis = this,
212
    const lthis = this,
213
        map = L.map(this.mapIdAttr, {zoomControl: true, gestureHandling: true}).setView([this.coordinates.lat, this.coordinates.lng], this.zoom),
213
        map = L.map(this.mapIdAttr, {zoomControl: true, gestureHandling: true}).setView([this.coordinates.lat, this.coordinates.lng], this.zoom),
214
        tileLayer = this.mapEl.dataset.layer || 'osm';
214
        tileLayer = this.mapEl.dataset.layer || 'osm';
215
 
215
 
216
    L.tileLayer(...tileLayers[tileLayer]).addTo(map);
216
    L.tileLayer(...tileLayers[tileLayer]).addTo(map);
217
 
217
 
218
    this.editableLayers = new L.FeatureGroup();
218
    this.editableLayers = new L.FeatureGroup();
219
    map.addLayer(this.editableLayers);
219
    map.addLayer(this.editableLayers);
220
 
220
 
221
    this.setDrawControl(map);
221
    this.setDrawControl(map);
222
 
222
 
223
    return map;
223
    return map;
224
};
224
};
225
 
225
 
226
Geoloc.prototype.setDrawControl = function(map) {
226
Geoloc.prototype.setDrawControl = function(map) {
227
    this.defaultDrawControlOptions = this.generateDrawControlOptions();
227
    this.defaultDrawControlOptions = this.generateDrawControlOptions();
228
    this.drawControl = this.generateDrawControl(...Object.values(this.defaultDrawControlOptions));
228
    this.drawControl = this.generateDrawControl(...Object.values(this.defaultDrawControlOptions));
229
    map.addControl(this.drawControl);
229
    map.addControl(this.drawControl);
230
};
230
};
231
 
231
 
232
Geoloc.prototype.generateDrawControlOptions = function() {
232
Geoloc.prototype.generateDrawControlOptions = function() {
233
    const options = {
233
    const options = {
234
        editOptions: false,
234
        editOptions: false,
235
        markerOptions: false,
235
        markerOptions: false,
236
        polylineOptions: false
236
        polylineOptions: false
237
    };
237
    };
238
 
238
 
239
    this.defaultEditOptions = {
239
    this.defaultEditOptions = {
240
        featureGroup: this.editableLayers,// REQUIRED!!
240
        featureGroup: this.editableLayers,// REQUIRED!!
241
        remove: true
241
        remove: true
242
    }
242
    }
243
 
243
 
244
    switch (this.geometryFilter) {
244
    switch (this.geometryFilter) {
245
        case 'point':
245
        case 'point':
246
            options.markerOptions = {
246
            options.markerOptions = {
247
                icon: new markerIcon(),
247
                icon: new markerIcon(),
248
                repeatMode: false
248
                repeatMode: false
249
            };
249
            };
250
            break;
250
            break;
251
        case 'rue':
251
        case 'rue':
252
            options.polylineOptions = defaultPolylineOptions;
252
            options.polylineOptions = defaultPolylineOptions;
253
            break;
253
            break;
254
        default:
254
        default:
255
            break;
255
            break;
256
    }
256
    }
257
 
257
 
258
    return options;
258
    return options;
259
};
259
};
260
 
260
 
261
Geoloc.prototype.generateDrawControl = function(
261
Geoloc.prototype.generateDrawControl = function(
262
    editOptions,
262
    editOptions,
263
    markerOptions = false,
263
    markerOptions = false,
264
    polylineOptions = false
264
    polylineOptions = false
265
) {
265
) {
266
    L.drawLocal = drawLocale;
266
    L.drawLocal = drawLocale;
267
 
267
 
268
    return new L.Control.Draw({
268
    return new L.Control.Draw({
269
        position: 'topleft',
269
        position: 'topleft',
270
        draw: {
270
        draw: {
271
            polyline: polylineOptions,
271
            polyline: polylineOptions,
272
            polygon: false,
272
            polygon: false,
273
            circle: false,
273
            circle: false,
274
            rectangle: false,
274
            rectangle: false,
275
            marker: markerOptions,
275
            marker: markerOptions,
276
            circlemarker: false
276
            circlemarker: false
277
        },
277
        },
278
        edit: editOptions
278
        edit: editOptions
279
    });
279
    });
280
};
280
};
281
 
281
 
282
Geoloc.prototype.onMarkerCreated = function() {
282
Geoloc.prototype.onMarkerCreated = function() {
283
    const coordinates = this.layer.getLatLng();
283
    const coordinates = this.layer.getLatLng();
284
 
284
 
285
    this.handleNewLocation(coordinates);
285
    this.handleNewLocation(coordinates);
286
};
286
};
287
 
287
 
288
Geoloc.prototype.handleMarkerEvents = function() {
288
Geoloc.prototype.handleMarkerEvents = function() {
289
    if(this.map) {
289
    if(this.map) {
290
        const lthis = this;
290
        const lthis = this;
291
        // move marker on click
291
        // move marker on click
292
        $(this.map).off('click').on('click', function(evt) {
292
        $(this.map).off('click').on('click', function(evt) {
293
            lthis.handleNewLocation(evt.originalEvent.latlng);
293
            lthis.handleNewLocation(evt.originalEvent.latlng);
294
        });
294
        });
295
        // move marker on drag
295
        // move marker on drag
296
        $(this.map.marker).off('dragend').on('dragend', function() {
296
        $(this.map.marker).off('dragend').on('dragend', function() {
297
            lthis.handleNewLocation(lthis.map.marker.getLatLng());
297
            lthis.handleNewLocation(lthis.map.marker.getLatLng());
298
        });
298
        });
299
    }
299
    }
300
};
300
};
301
 
301
 
302
Geoloc.prototype.handlePolylineEvents = function(requiresNewEditDrawControl = true) {
302
Geoloc.prototype.handlePolylineEvents = function(requiresNewEditDrawControl = true) {
303
    const latLngs = this.layer.getLatLngs(),
303
    const latLngs = this.layer.getLatLngs(),
304
        polyline = this.formatPolyline(latLngs),
304
        polyline = this.formatPolyline(latLngs),
305
        coordinates = this.layer.getBounds().getCenter();
305
        coordinates = this.layer.getBounds().getCenter();
306
 
306
 
307
 
307
 
308
    if (requiresNewEditDrawControl) {
308
    if (requiresNewEditDrawControl) {
309
        this.drawControl = this.generateDrawControl(this.defaultEditOptions);
309
        this.drawControl = this.generateDrawControl(this.defaultEditOptions);
310
        this.map.addControl(this.drawControl);
310
        this.map.addControl(this.drawControl);
311
    }
311
    }
312
 
312
 
313
    // make polyline removable
313
    // make polyline removable
314
    this.editableLayers.addLayer(L.polyline(latLngs));
314
    this.editableLayers.addLayer(L.polyline(latLngs));
315
 
315
 
316
    this.map.addLayer(this.layer);
316
    this.map.addLayer(this.layer);
317
    this.handleNewLocation(coordinates, polyline);
317
    this.handleNewLocation(coordinates, polyline);
318
};
318
};
319
 
319
 
320
/**
320
/**
321
 * triggers location event
321
 * triggers location event
322
 * @param coordinates.
322
 * @param coordinates.
323
 * @param coordinates.lat latitude.
323
 * @param coordinates.lat latitude.
324
 * @param coordinates.lng longitude.
324
 * @param coordinates.lng longitude.
325
 * @param {array||null} polyline array of coordinates object
325
 * @param {array||null} polyline array of coordinates object
326
 */
326
 */
327
Geoloc.prototype.handleNewLocation = function (coordinates, polyline = []) {
327
Geoloc.prototype.handleNewLocation = function (coordinates, polyline = []) {
328
    coordinates = this.formatCoordinates(coordinates);
328
    coordinates = this.formatCoordinates(coordinates);
329
 
329
 
330
    if(!!coordinates && !!coordinates.lat && coordinates.lng) {
330
    if(!!coordinates && !!coordinates.lat && coordinates.lng) {
331
        this.zoom = 20;
331
        this.zoom = 20;
332
        this.setMapCoordinates(coordinates);
332
        this.setMapCoordinates(coordinates);
333
 
333
 
334
        if('point' === this.geometryFilter) {
334
        if('point' === this.geometryFilter) {
335
            this.createDraggableMarker();
335
            this.createDraggableMarker();
336
            this.handleMarkerEvents();
336
            this.handleMarkerEvents();
337
        }
337
        }
338
 
338
 
339
        if (
339
        if (
340
            ('rue' === this.geometryFilter && 0 < polyline.length) ||
340
            ('rue' === this.geometryFilter && 0 < polyline.length) ||
341
            ('point' === this.geometryFilter && 0 === polyline.length)
341
            ('point' === this.geometryFilter && 0 === polyline.length)
342
        ) {
342
        ) {
343
            this.getLocationInfo(coordinates, polyline);
343
            this.getLocationInfo(coordinates, polyline);
344
        }
344
        }
345
    }
345
    }
346
};
346
};
347
 
347
 
348
Geoloc.prototype.formatCoordinates = function (coordinates) {
348
Geoloc.prototype.formatCoordinates = function (coordinates) {
349
    coordinates.lat = Number.parseFloat(coordinates.lat);
349
    coordinates.lat = Number.parseFloat(coordinates.lat);
350
    coordinates.lng = Number.parseFloat(coordinates.lng);
350
    coordinates.lng = Number.parseFloat(coordinates.lng);
351
 
351
 
352
    if(Number.isNaN(coordinates.lat) || Number.isNaN(coordinates.lng)) {
352
    if(Number.isNaN(coordinates.lat) || Number.isNaN(coordinates.lng)) {
353
        return null;
353
        return null;
354
    }
354
    }
355
 
355
 
356
    return coordinates;
356
    return coordinates;
357
};
357
};
358
 
358
 
359
Geoloc.prototype.formatPolyline = function (latLngs) {
359
Geoloc.prototype.formatPolyline = function (latLngs) {
360
    const polyline = [];
360
    const polyline = [];
361
 
361
 
362
    latLngs.forEach(coordinates => polyline.push(Object.values(coordinates).reverse()));
362
    latLngs.forEach(coordinates => polyline.push(Object.values(coordinates).reverse()));
363
 
363
 
364
    return polyline;
364
    return polyline;
365
};
365
};
366
 
366
 
367
Geoloc.prototype.setMapCoordinates = function (coordinates) {
367
Geoloc.prototype.setMapCoordinates = function (coordinates) {
368
    this.coordinates = coordinates;
368
    this.coordinates = coordinates;
369
    // updates map
369
    // updates map
370
    this.map.setView(coordinates,this.zoom);
370
    this.map.setView(coordinates,this.zoom);
371
};
371
};
372
 
372
 
373
Geoloc.prototype.createDraggableMarker = function() {
373
Geoloc.prototype.createDraggableMarker = function() {
374
    if (undefined === this.map.marker) {
374
    if (undefined === this.map.marker) {
375
        // after many attempts, did not manage
375
        // after many attempts, did not manage
376
        // to make marker from draw control draggable
376
        // to make marker from draw control draggable
377
        // solution: replace it
377
        // solution: replace it
378
        if(this.layer) {
378
        if(this.layer) {
379
            this.map.removeLayer(this.layer);
379
            this.map.removeLayer(this.layer);
380
        }
380
        }
381
        this.map.marker = new L.Marker(this.coordinates, {
381
        this.map.marker = new L.Marker(this.coordinates, {
382
            draggable: true,
382
            draggable: true,
383
            icon: new markerIcon()
383
            icon: new markerIcon()
384
        });
384
        });
385
        this.layer = this.map.marker;
385
        this.layer = this.map.marker;
386
        this.map.addLayer(this.map.marker);
386
        this.map.addLayer(this.map.marker);
387
        if(this.drawControl) {
387
        if(this.drawControl) {
388
            this.map.removeControl(this.drawControl);
388
            this.map.removeControl(this.drawControl);
389
        }
389
        }
390
    }
390
    }
391
 
391
 
392
    this.map.marker.setLatLng(this.coordinates, {draggable: 'true'});
392
    this.map.marker.setLatLng(this.coordinates, {draggable: 'true'});
393
};
393
};
394
 
394
 
395
Geoloc.prototype.getLocationInfo = function(coordinates, polyline) {
395
Geoloc.prototype.getLocationInfo = function(coordinates, polyline) {
396
    const lthis = this,
396
    const lthis = this,
397
        url = NOMINATIM_OSM_URL+'reverse',
397
        url = NOMINATIM_OSM_URL+'reverse',
398
        params = {
398
        params = {
399
            'format': 'json',
399
            'format': 'json',
400
            'lat': coordinates.lat,
400
            'lat': coordinates.lat,
401
            'lon': coordinates.lng
401
            'lon': coordinates.lng
402
        };
402
        };
403
 
403
 
404
    this.geolocLabel.classList.add('loading');
404
    this.geolocLabel.classList.add('loading');
405
 
405
 
406
    $.ajax({
406
    $.ajax({
407
        method: "GET",
407
        method: "GET",
408
        url: url,
408
        url: url,
409
        data: params,
409
        data: params,
410
        success: function(locationData) {
410
        success: function(locationData) {
411
            locationData.centroid = lthis.formatPointTypeCoordinates(coordinates);
411
            locationData.centroid = lthis.formatPointTypeCoordinates(coordinates);
412
            locationData.geojson = 'rue' === lthis.geometryFilter ? {type: 'LineString', coordinates: polyline} : locationData.centroid;
412
            locationData.geojson = 'rue' === lthis.geometryFilter ? {type: 'LineString', coordinates: polyline} : locationData.centroid;
413
            lthis.loadGeolocation(coordinates,locationData);
413
            lthis.loadGeolocation(coordinates,locationData);
414
        },
414
        },
415
        error: (err) => {
415
        error: (err) => {
416
            console.warn(err);
416
            console.warn(err);
417
            lthis.geolocLabel.classList.remove('loading');
417
            lthis.geolocLabel.classList.remove('loading');
418
        }
418
        }
419
    });
419
    });
420
};
420
};
421
 
421
 
422
Geoloc.prototype.formatPointTypeCoordinates = function(coordinates) {
422
Geoloc.prototype.formatPointTypeCoordinates = function(coordinates) {
423
    return {type : 'Point', coordinates: Object.values(coordinates).reverse()};
423
    return {type : 'Point', coordinates: Object.values(coordinates).reverse()};
424
};
424
};
425
 
425
 
426
Geoloc.prototype.loadGeolocation = function(coordinates,locationData) {
426
Geoloc.prototype.loadGeolocation = function(coordinates,locationData) {
427
    const lthis = this,
427
    const lthis = this,
428
        query = {
428
        query = {
429
            'lat': coordinates.lat,
429
            'lat': coordinates.lat,
430
            'lon': coordinates.lng
430
            'lon': coordinates.lng
431
        };
431
        };
432
 
432
 
433
    $.ajax({
433
    $.ajax({
434
        method: "GET",
434
        method: "GET",
435
        url: URL_GEOLOC_SERVICE,
435
        url: URL_GEOLOC_SERVICE,
436
        data: query,
436
        data: query,
437
        success: function (geoLocationData) {
437
        success: function (geoLocationData) {
438
            lthis.triggerLocationEvent(
438
            lthis.triggerLocationEvent(
439
                lthis.formatLocationEventObject(locationData,geoLocationData)
439
                lthis.formatLocationEventObject(locationData,geoLocationData)
440
            );
440
            );
441
            lthis.geolocLabel.classList.remove('loading');
441
            lthis.geolocLabel.classList.remove('loading');
442
        },
442
        },
443
        error:  (err) => {
443
        error:  (err) => {
444
            console.warn(err);
444
            console.warn(err);
445
            lthis.geolocLabel.classList.remove('loading');
445
            lthis.geolocLabel.classList.remove('loading');
446
        }
446
        }
447
    });
447
    });
448
};
448
};
449
 
449
 
450
Geoloc.prototype.triggerLocationEvent = function(locationDataObject) {
450
Geoloc.prototype.triggerLocationEvent = function(locationDataObject) {
451
    const locationEvent = new CustomEvent('location', {detail: locationDataObject});
451
    const locationEvent = new CustomEvent('location', {detail: locationDataObject});
452
 
452
 
453
    this.mapEl.dispatchEvent(locationEvent);
453
    this.mapEl.dispatchEvent(locationEvent);
454
};
454
};
455
 
455
 
456
Geoloc.prototype.formatLocationEventObject = function(locationData,geoLocationData) {
456
Geoloc.prototype.formatLocationEventObject = function(locationData,geoLocationData) {
457
    const detail = {
457
    const detail = {
458
        centroid: locationData.centroid,
458
        centroid: locationData.centroid,
459
        geometry: locationData.geojson,
459
        geometry: locationData.geojson,
460
        elevation: geoLocationData.altitude,
460
        elevation: geoLocationData.altitude,
461
        inseeData: {
461
        inseeData: {
462
            code: 'FR' === geoLocationData.code_pays ? geoLocationData.code_zone : '',
462
            code: 'FR' === geoLocationData.code_pays ? geoLocationData.code_zone : '',
463
            nom: geoLocationData.nom
463
            nom: geoLocationData.nom
464
        },
464
        },
465
        osmCountry: locationData.address.country,
465
        osmCountry: locationData.address.country,
466
        osmCountryCode: geoLocationData.code_pays,
466
        osmCountryCode: geoLocationData.code_pays,
467
        osmCounty: locationData.address.county,
467
        osmCounty: locationData.address.county,
468
        osmPostcode: locationData.address.postcode,
468
        osmPostcode: locationData.address.postcode,
469
        locality: this.getLocalityFromData(locationData),
469
        locality: this.getLocalityFromData(locationData),
470
        locality: geoLocationData.nom,
470
        locality: geoLocationData.nom,
471
        osmRoad: locationData.address.road,
471
        osmRoad: locationData.address.road,
472
        osmState: locationData.address.state,
472
        osmState: locationData.address.state,
473
        osmId: locationData.osm_id,
473
        osmId: locationData.osm_id,
474
        osmPlaceId: locationData.place_id
474
        osmPlaceId: locationData.place_id
475
    };
475
    };
476
 
476
 
477
    return detail;
477
    return detail;
478
};
478
};
479
 
479
 
480
Geoloc.prototype.handleCoordinates = function() {
480
Geoloc.prototype.handleCoordinates = function() {
481
    if (!!this.latitudeEl.value && !!this.longitudeEl.value) {
481
    if (!!this.latitudeEl.value && !!this.longitudeEl.value) {
482
        this.handleNewLocation({
482
        this.handleNewLocation({
483
            'lat': this.latitudeEl.value,
483
            'lat': this.latitudeEl.value,
484
            'lng': this.longitudeEl.value
484
            'lng': this.longitudeEl.value
485
        });
485
        });
486
    }
486
    }
487
};
487
};
488
 
488
 
489
Geoloc.prototype.onCoordinates = function() {
489
Geoloc.prototype.onCoordinates = function() {
490
    [this.latitudeEl,this.longitudeEl].forEach(coordinate =>
490
    [this.latitudeEl,this.longitudeEl].forEach(coordinate =>
491
        coordinate.addEventListener('blur', function() {
491
        coordinate.addEventListener('blur', function() {
492
            this.handleCoordinates();
492
            this.handleCoordinates();
493
        }.bind(this))
493
        }.bind(this))
494
    );
494
    );
495
};
495
};
496
 
496
 
497
Geoloc.prototype.initSearchLocality = function() {
497
Geoloc.prototype.initSearchLocality = function() {
498
    const placesZone = document.getElementById('tb-places-zone');
498
    const placesZone = document.getElementById('tb-places-zone');
499
 
499
 
500
    if(placesZone) {
500
    if(placesZone) {
501
        placesZone.classList.remove('hidden');
501
        placesZone.classList.remove('hidden');
502
        this.tbPlaces = new TbPlaces(this.tbPlacesCallback.bind(this));
502
        this.tbPlaces = new TbPlaces(this.tbPlacesCallback.bind(this));
503
        this.tbPlaces.init();
503
        this.tbPlaces.init();
504
    }
504
    }
505
};
505
};
506
 
506
 
507
Geoloc.prototype.tbPlacesCallback = function(localityData) {
507
Geoloc.prototype.tbPlacesCallback = function(localityData) {
508
    const locality = this.getLocalityFromData(localityData);
508
    const locality = this.getLocalityFromData(localityData);
509
 
509
 
510
    if(!!locality) {
510
    if(!!locality) {
511
        const coordinates = this.formatCoordinates({
511
        const coordinates = this.formatCoordinates({
512
            'lat' : localityData.lat,
512
            'lat' : localityData.lat,
513
            'lng' : localityData.lon
513
            'lng' : localityData.lon
514
        });
514
        });
515
 
515
 
516
        if(!!coordinates && !!coordinates.lat && !!coordinates.lng) {
516
        if(!!coordinates && !!coordinates.lat && !!coordinates.lng) {
517
            this.zoom = 20;
517
            this.zoom = 20;
518
            this.setMapCoordinates(coordinates);
518
            this.setMapCoordinates(coordinates);
519
 
519
 
520
            if('point' === this.geometryFilter) {
520
            if('point' === this.geometryFilter) {
521
                this.map.removeControl(this.drawControl);
521
                this.map.removeControl(this.drawControl);
522
                this.createDraggableMarker();
522
                this.createDraggableMarker();
523
                this.handleMarkerEvents();
523
                this.handleMarkerEvents();
524
            }
524
            }
525
 
525
 
526
            localityData.centroid = this.formatPointTypeCoordinates(coordinates);
526
            localityData.centroid = this.formatPointTypeCoordinates(coordinates);
527
            if('rue' !== this.geometryFilter && 'Polygon' === localityData.geojson.type ) {
527
            if('rue' !== this.geometryFilter && 'Polygon' === localityData.geojson.type ) {
528
                localityData.geojson = localityData.centroid;
528
                localityData.geojson = localityData.centroid;
529
            }
529
            }
530
            this.loadGeolocation(coordinates,localityData);
530
            this.loadGeolocation(coordinates,localityData);
531
        }
531
        }
532
    }
532
    }
533
};
533
};
534
 
534
 
535
Geoloc.prototype.getLocalityFromData = function(localityData) {
535
Geoloc.prototype.getLocalityFromData = function(localityData) {
536
    const addressData = localityData.address,
536
    const addressData = localityData.address,
537
 
537
 
538
        locationNameType = ['village', 'city', 'locality', 'municipality', 'county', 'state'].find(locationNameType => addressData[locationNameType] !== undefined);
538
        locationNameType = ['village', 'city', 'locality', 'municipality', 'county', 'state'].find(locationNameType => addressData[locationNameType] !== undefined);
539
    if (!locationNameType) {
539
    if (!locationNameType) {
540
        return;
540
        return;
541
    }
541
    }
542
 
542
 
543
    return addressData[locationNameType];
543
    return addressData[locationNameType];
544
};
544
};
545
 
545
 
546
Geoloc.prototype.closeMap = function () {
546
Geoloc.prototype.closeMap = function () {
547
    // reset map
547
    // reset map
548
    this.map = L.DomUtil.get(this.mapIdAttr);
548
    this.map = L.DomUtil.get(this.mapIdAttr);
549
    if (this.map != null) {
549
    if (this.map != null) {
550
        this.map._leaflet_id = null;
550
        this.map._leaflet_id = null;
551
    }
551
    }
552
};
552
};