From be69f7ea8f58b65cfe164ac77ec5feb74755fb76 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 21 Aug 2021 16:12:32 -0700 Subject: Support MapTiler maps --- modern/src/map/Map.js | 15 ++++++++++++--- modern/src/map/switcher/switcher.js | 11 +++++++++-- 2 files changed, 21 insertions(+), 5 deletions(-) (limited to 'modern') diff --git a/modern/src/map/Map.js b/modern/src/map/Map.js index 7dd1c2a8..c2861ed5 100644 --- a/modern/src/map/Map.js +++ b/modern/src/map/Map.js @@ -7,7 +7,7 @@ import React, { import { SwitcherControl } from './switcher/switcher'; import deviceCategories from '../common/deviceCategories'; import { prepareIcon, loadImage } from './mapUtil'; -import { styleCarto, styleMapbox, styleOsm } from './mapStyles'; +import { styleCarto, styleMapbox, styleMapTiler, styleOsm } from './mapStyles'; import t from '../common/localization'; import { useAttributePreference } from '../common/preferences'; import palette from '../theme/palette'; @@ -64,13 +64,14 @@ map.addControl(new maplibregl.NavigationControl({ showCompass: false, })); -map.addControl(new SwitcherControl( +const switcher = new SwitcherControl( [ { title: t('mapOsm'), uri: styleOsm() }, { title: t('mapCarto'), uri: styleCarto() }, { title: t('mapMapboxStreets'), uri: styleMapbox('streets-v11') }, { title: t('mapMapboxOutdoors'), uri: styleMapbox('outdoors-v11') }, { title: t('mapMapboxSatellite'), uri: styleMapbox('satellite-v9') }, + { title: t('mapMapTilerBasic'), uri: styleMapTiler('basic', '${mapTilerKey}') }, ], t('mapOsm'), () => updateReadyValue(false), @@ -84,7 +85,9 @@ map.addControl(new SwitcherControl( }; waiting(); }, -)); +); + +map.addControl(switcher); const Map = ({ children }) => { const containerEl = useRef(null); @@ -97,6 +100,12 @@ const Map = ({ children }) => { maplibregl.accessToken = mapboxAccessToken; }, [mapboxAccessToken]); + const mapTilerKey = useAttributePreference('mapTilerKey'); + + useEffect(() => { + switcher.setVariable('mapTilerKey', mapTilerKey); + }, [mapTilerKey]); + useEffect(() => { const listener = (ready) => setMapReady(ready); addReadyListener(listener); diff --git a/modern/src/map/switcher/switcher.js b/modern/src/map/switcher/switcher.js index e9076aa6..014a35e0 100644 --- a/modern/src/map/switcher/switcher.js +++ b/modern/src/map/switcher/switcher.js @@ -5,12 +5,17 @@ export class SwitcherControl { this.beforeSwitch = beforeSwitch; this.afterSwitch = afterSwitch; this.onDocumentClick = this.onDocumentClick.bind(this); + this.variables = {}; } getDefaultPosition() { return 'top-right'; } + setVariable(key, value) { + this.variables[key] = value; + } + onAdd(map) { this.map = map; this.controlContainer = document.createElement('div'); @@ -25,14 +30,16 @@ export class SwitcherControl { styleElement.type = 'button'; styleElement.innerText = style.title; styleElement.classList.add(style.title.replace(/[^a-z0-9-]/gi, '_')); - styleElement.dataset.uri = JSON.stringify(style.uri); + styleElement.dataset.uri = style.uri; styleElement.addEventListener('click', (event) => { const { srcElement } = event; if (srcElement.classList.contains('active')) { return; } this.beforeSwitch(); - this.map.setStyle(JSON.parse(srcElement.dataset.uri)); + let uri = srcElement.dataset.uri; + Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`\$\{${key}\}`, value)); + this.map.setStyle(uri); this.afterSwitch(); this.mapStyleContainer.style.display = 'none'; this.styleButton.style.display = 'block'; -- cgit v1.2.3 From 75e62d6f56bffb8d4fd18ce7d2d9077821095c85 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 21 Aug 2021 16:13:36 -0700 Subject: Remove unnecessary escaping --- modern/src/map/switcher/switcher.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'modern') diff --git a/modern/src/map/switcher/switcher.js b/modern/src/map/switcher/switcher.js index 014a35e0..643b6ec0 100644 --- a/modern/src/map/switcher/switcher.js +++ b/modern/src/map/switcher/switcher.js @@ -38,7 +38,7 @@ export class SwitcherControl { } this.beforeSwitch(); let uri = srcElement.dataset.uri; - Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`\$\{${key}\}`, value)); + Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`$\{${key}}`, value)); this.map.setStyle(uri); this.afterSwitch(); this.mapStyleContainer.style.display = 'none'; -- cgit v1.2.3 From 230b5b53460982ef888d309725f027ea29b29bb6 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 21 Aug 2021 16:46:15 -0700 Subject: Fix map switches --- modern/src/map/Map.js | 30 ++++++++++++++++-------------- modern/src/map/switcher/switcher.js | 8 +++++--- 2 files changed, 21 insertions(+), 17 deletions(-) (limited to 'modern') diff --git a/modern/src/map/Map.js b/modern/src/map/Map.js index c2861ed5..3afa48df 100644 --- a/modern/src/map/Map.js +++ b/modern/src/map/Map.js @@ -40,21 +40,23 @@ const updateReadyValue = (value) => { const initMap = async () => { if (ready) return; - const background = await loadImage('images/background.svg'); - map.addImage('background', await prepareIcon(background), { - pixelRatio: window.devicePixelRatio, - }); - await Promise.all(deviceCategories.map(async (category) => { - const results = []; - ['green', 'red', 'gray'].forEach((color) => { - results.push(loadImage(`images/icon/${category}.svg`).then((icon) => { - map.addImage(`${category}-${color}`, prepareIcon(background, icon, palette.common[color]), { - pixelRatio: window.devicePixelRatio, - }); - })); + if (!map.hasImage('background')) { + const background = await loadImage('images/background.svg'); + map.addImage('background', await prepareIcon(background), { + pixelRatio: window.devicePixelRatio, }); - await Promise.all(results); - })); + await Promise.all(deviceCategories.map(async (category) => { + const results = []; + ['green', 'red', 'gray'].forEach((color) => { + results.push(loadImage(`images/icon/${category}.svg`).then((icon) => { + map.addImage(`${category}-${color}`, prepareIcon(background, icon, palette.common[color]), { + pixelRatio: window.devicePixelRatio, + }); + })); + }); + await Promise.all(results); + })); + } updateReadyValue(true); }; diff --git a/modern/src/map/switcher/switcher.js b/modern/src/map/switcher/switcher.js index 643b6ec0..a3805f6b 100644 --- a/modern/src/map/switcher/switcher.js +++ b/modern/src/map/switcher/switcher.js @@ -30,15 +30,17 @@ export class SwitcherControl { styleElement.type = 'button'; styleElement.innerText = style.title; styleElement.classList.add(style.title.replace(/[^a-z0-9-]/gi, '_')); - styleElement.dataset.uri = style.uri; + styleElement.dataset.uri = JSON.stringify(style.uri); styleElement.addEventListener('click', (event) => { const { srcElement } = event; if (srcElement.classList.contains('active')) { return; } this.beforeSwitch(); - let uri = srcElement.dataset.uri; - Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`$\{${key}}`, value)); + let uri = JSON.parse(srcElement.dataset.uri); + if (typeof uri === 'string') { + Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`$\{${key}}`, value)); + } this.map.setStyle(uri); this.afterSwitch(); this.mapStyleContainer.style.display = 'none'; -- cgit v1.2.3 From afed83a89ecea62f7f1fd3ae3c99cdf95e52dab6 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 21 Aug 2021 16:48:19 -0700 Subject: Fix style --- modern/src/map/Map.js | 6 ++++-- modern/src/map/switcher/switcher.js | 2 +- 2 files changed, 5 insertions(+), 3 deletions(-) (limited to 'modern') diff --git a/modern/src/map/Map.js b/modern/src/map/Map.js index 3afa48df..6f4875ad 100644 --- a/modern/src/map/Map.js +++ b/modern/src/map/Map.js @@ -7,7 +7,9 @@ import React, { import { SwitcherControl } from './switcher/switcher'; import deviceCategories from '../common/deviceCategories'; import { prepareIcon, loadImage } from './mapUtil'; -import { styleCarto, styleMapbox, styleMapTiler, styleOsm } from './mapStyles'; +import { + styleCarto, styleMapbox, styleMapTiler, styleOsm, +} from './mapStyles'; import t from '../common/localization'; import { useAttributePreference } from '../common/preferences'; import palette from '../theme/palette'; @@ -73,7 +75,7 @@ const switcher = new SwitcherControl( { title: t('mapMapboxStreets'), uri: styleMapbox('streets-v11') }, { title: t('mapMapboxOutdoors'), uri: styleMapbox('outdoors-v11') }, { title: t('mapMapboxSatellite'), uri: styleMapbox('satellite-v9') }, - { title: t('mapMapTilerBasic'), uri: styleMapTiler('basic', '${mapTilerKey}') }, + { title: t('mapMapTilerBasic'), uri: styleMapTiler('basic', '{mapTilerKey}') }, ], t('mapOsm'), () => updateReadyValue(false), diff --git a/modern/src/map/switcher/switcher.js b/modern/src/map/switcher/switcher.js index a3805f6b..cb7326f4 100644 --- a/modern/src/map/switcher/switcher.js +++ b/modern/src/map/switcher/switcher.js @@ -39,7 +39,7 @@ export class SwitcherControl { this.beforeSwitch(); let uri = JSON.parse(srcElement.dataset.uri); if (typeof uri === 'string') { - Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`$\{${key}}`, value)); + Object.entries(this.variables).forEach(([key, value]) => uri = uri.replaceAll(`\{${key}}`, value)); } this.map.setStyle(uri); this.afterSwitch(); -- cgit v1.2.3 From 90b87123fe6597e080d2ab03463f50617cd2c5dd Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sat, 21 Aug 2021 17:31:38 -0700 Subject: Fix map switches --- modern/src/map/AccuracyMap.js | 8 ++++++-- modern/src/map/GeofenceMap.js | 16 ++++++++++++---- modern/src/map/PositionsMap.js | 12 +++++++++--- modern/src/map/ReplayPathMap.js | 8 ++++++-- 4 files changed, 33 insertions(+), 11 deletions(-) (limited to 'modern') diff --git a/modern/src/map/AccuracyMap.js b/modern/src/map/AccuracyMap.js index 4baa1054..5734ee82 100644 --- a/modern/src/map/AccuracyMap.js +++ b/modern/src/map/AccuracyMap.js @@ -36,8 +36,12 @@ const AccuracyMap = () => { }); return () => { - map.removeLayer(id); - map.removeSource(id); + if (map.getLayer(id)) { + map.removeLayer(id); + } + if (map.getSource(id)) { + map.removeSource(id); + } }; }, []); diff --git a/modern/src/map/GeofenceMap.js b/modern/src/map/GeofenceMap.js index d00cbb18..c0ecef40 100644 --- a/modern/src/map/GeofenceMap.js +++ b/modern/src/map/GeofenceMap.js @@ -56,10 +56,18 @@ const GeofenceMap = () => { }); return () => { - map.removeLayer('geofences-fill'); - map.removeLayer('geofences-line'); - map.removeLayer('geofences-title'); - map.removeSource(id); + if (map.getLayer('geofences-fill')) { + map.removeLayer('geofences-fill'); + } + if (map.getLayer('geofences-line')) { + map.removeLayer('geofences-line'); + } + if (map.getLayer('geofences-title')) { + map.removeLayer('geofences-title'); + } + if (map.getSource(id)) { + map.removeSource(id); + } }; }, []); diff --git a/modern/src/map/PositionsMap.js b/modern/src/map/PositionsMap.js index 9719b45b..8d100534 100644 --- a/modern/src/map/PositionsMap.js +++ b/modern/src/map/PositionsMap.js @@ -148,9 +148,15 @@ const PositionsMap = ({ positions }) => { map.off('click', id, onMarkerClick); map.off('click', clusters, onClusterClick); - map.removeLayer(id); - map.removeLayer(clusters); - map.removeSource(id); + if (map.getLayer(id)) { + map.removeLayer(id); + } + if (map.getLayer(clusters)) { + map.removeLayer(clusters); + } + if (map.getSource(id)) { + map.removeSource(id); + } }; }, [onMarkerClick]); diff --git a/modern/src/map/ReplayPathMap.js b/modern/src/map/ReplayPathMap.js index 62b3f279..022548b7 100644 --- a/modern/src/map/ReplayPathMap.js +++ b/modern/src/map/ReplayPathMap.js @@ -31,8 +31,12 @@ const ReplayPathMap = ({ positions }) => { }); return () => { - map.removeLayer(id); - map.removeSource(id); + if (map.getLayer(id)) { + map.removeLayer(id); + } + if (map.getSource(id)) { + map.removeSource(id); + } }; }, []); -- cgit v1.2.3 From e83a51c9f14b7ddb45e4de155741e37df3e25c25 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sun, 22 Aug 2021 10:11:46 -0700 Subject: Add MapTiler hybrid map --- modern/src/map/Map.js | 1 + web/l10n/en.json | 1 + 2 files changed, 2 insertions(+) (limited to 'modern') diff --git a/modern/src/map/Map.js b/modern/src/map/Map.js index 6f4875ad..47ebb1f0 100644 --- a/modern/src/map/Map.js +++ b/modern/src/map/Map.js @@ -76,6 +76,7 @@ const switcher = new SwitcherControl( { title: t('mapMapboxOutdoors'), uri: styleMapbox('outdoors-v11') }, { title: t('mapMapboxSatellite'), uri: styleMapbox('satellite-v9') }, { title: t('mapMapTilerBasic'), uri: styleMapTiler('basic', '{mapTilerKey}') }, + { title: t('mapMapTilerHybrid'), uri: styleMapTiler('hybrid', '{mapTilerKey}') }, ], t('mapOsm'), () => updateReadyValue(false), diff --git a/web/l10n/en.json b/web/l10n/en.json index af20b1a4..97243a69 100644 --- a/web/l10n/en.json +++ b/web/l10n/en.json @@ -262,6 +262,7 @@ "mapMapboxOutdoors": "Mapbox Outdoors", "mapMapboxSatellite": "Mapbox Satellite", "mapMapTilerBasic": "MapTiler Basic", + "mapMapTilerHybrid": "MapTiler Hybrid", "mapShapePolygon": "Polygon", "mapShapeCircle": "Circle", "mapShapePolyline": "Polyline", -- cgit v1.2.3