ol-elevation-profile 2.1.0 → 2.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/ol-elevation-profile.d.ts +24 -8
- package/dist/ol-elevation-profile.esm.js +51 -14
- package/dist/ol-elevation-profile.esm.min.js +2 -2
- package/dist/ol-elevation-profile.js +51 -14
- package/dist/ol-elevation-profile.min.js +2 -2
- package/package.json +1 -1
- package/src/ol-elevation-profile.js +49 -12
|
@@ -262,12 +262,20 @@ export type ElevationProfileOptions = {
|
|
|
262
262
|
* `{exaggeration}` fixes the ratio between the two axes instead, which makes SLOPES
|
|
263
263
|
* comparable: the gradient read off the chart is the real one, multiplied by the same
|
|
264
264
|
* factor on every track, and the control recomputes it per track and per A/B crop.
|
|
265
|
-
*
|
|
266
|
-
*
|
|
267
|
-
*
|
|
265
|
+
* `{maxExaggeration}` keeps `'auto'` — the height is filled, which reads best — and
|
|
266
|
+
* only reins in the absurd: a short, gently sloping track whose 2 % ramp would
|
|
267
|
+
* otherwise be drawn as a wall. A track already under the cap is untouched, so unlike
|
|
268
|
+
* a fixed exaggeration it never flattens a mountain traverse to fit a rule.
|
|
269
|
+
* A number or `{exaggeration}` is a **floor**, not a cage: a track whose range exceeds
|
|
270
|
+
* what the height can show would spill out of the frame, which is worse than losing
|
|
271
|
+
* comparability, so the scale then widens silently, nothing being drawn on the chart
|
|
272
|
+
* to say so. The extra room the scale asks for is added ABOVE the track, never below:
|
|
273
|
+
* centring it would push the axis under sea level on a mountain profile.
|
|
268
274
|
*/
|
|
269
275
|
verticalScale?: ('auto' | number | {
|
|
270
276
|
exaggeration: number;
|
|
277
|
+
} | {
|
|
278
|
+
maxExaggeration: number;
|
|
271
279
|
});
|
|
272
280
|
/**
|
|
273
281
|
* How a track is selected on the map.
|
|
@@ -419,16 +427,22 @@ export type ElevationProfileOptions = {
|
|
|
419
427
|
* @property {number} [smoothing=0] Elevation smoothing window, in METERS (0 = none).
|
|
420
428
|
* @property {?number} [xTicks=null] X axis ticks (null = auto from width).
|
|
421
429
|
* @property {?number} [yTicks=null] Y axis ticks (null = auto from height).
|
|
422
|
-
* @property {('auto'|number|{exaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
430
|
+
* @property {('auto'|number|{exaggeration:number}|{maxExaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
423
431
|
* profile fills the height, which is legible but changes scale from one track to the
|
|
424
432
|
* next, so a 2 % ramp looks like a wall and two profiles cannot be compared. A number
|
|
425
433
|
* fixes the metres covered per physical centimetre, which makes RANGES comparable.
|
|
426
434
|
* `{exaggeration}` fixes the ratio between the two axes instead, which makes SLOPES
|
|
427
435
|
* comparable: the gradient read off the chart is the real one, multiplied by the same
|
|
428
436
|
* factor on every track, and the control recomputes it per track and per A/B crop.
|
|
429
|
-
*
|
|
430
|
-
*
|
|
431
|
-
*
|
|
437
|
+
* `{maxExaggeration}` keeps `'auto'` — the height is filled, which reads best — and
|
|
438
|
+
* only reins in the absurd: a short, gently sloping track whose 2 % ramp would
|
|
439
|
+
* otherwise be drawn as a wall. A track already under the cap is untouched, so unlike
|
|
440
|
+
* a fixed exaggeration it never flattens a mountain traverse to fit a rule.
|
|
441
|
+
* A number or `{exaggeration}` is a **floor**, not a cage: a track whose range exceeds
|
|
442
|
+
* what the height can show would spill out of the frame, which is worse than losing
|
|
443
|
+
* comparability, so the scale then widens silently, nothing being drawn on the chart
|
|
444
|
+
* to say so. The extra room the scale asks for is added ABOVE the track, never below:
|
|
445
|
+
* centring it would push the axis under sea level on a mountain profile.
|
|
432
446
|
* @property {'click'|'mouseover'} [show='click'] How a track is selected on the map.
|
|
433
447
|
* @property {boolean} [showWithoutElevation=true] What to do with a track that ends up
|
|
434
448
|
* with no elevation at all: none in its geometry, and none the terrain model could
|
|
@@ -742,7 +756,9 @@ declare class ElevationProfile extends Control {
|
|
|
742
756
|
*
|
|
743
757
|
* @private
|
|
744
758
|
*/
|
|
745
|
-
private
|
|
759
|
+
/** Le rapport à ne pas dépasser, `0` s'il n'en est pas demandé. @private */
|
|
760
|
+
private _plafondExageration;
|
|
761
|
+
_verticalScaleFor(s: any, innerW: any): number;
|
|
746
762
|
_statsOf(samples: any, fromTotal: any): {
|
|
747
763
|
distance: number;
|
|
748
764
|
duration: number;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! ol-elevation-profile 2.1.
|
|
1
|
+
/*! ol-elevation-profile 2.1.2 | MIT License | https://github.com/lc-4918/ol-elevation-profile */
|
|
2
2
|
import Control from 'ol/control/Control.js';
|
|
3
3
|
import Overlay from 'ol/Overlay.js';
|
|
4
4
|
import { unByKey } from 'ol/Observable.js';
|
|
@@ -116,7 +116,8 @@ import * as d3 from 'd3';
|
|
|
116
116
|
yTicks: null,
|
|
117
117
|
verticalScale: 'auto', // 'auto' : le profil remplit la hauteur ;
|
|
118
118
|
// un nombre : mètres par centimètre physique ;
|
|
119
|
-
// { exaggeration } : rapport fixe vertical/horizontal
|
|
119
|
+
// { exaggeration } : rapport fixe vertical/horizontal ;
|
|
120
|
+
// { maxExaggeration } : 'auto' sans dépasser ce rapport
|
|
120
121
|
show: 'click',
|
|
121
122
|
showWithoutElevation: true, // trace sans Z, et aucun MNT n'a pu en fournir :
|
|
122
123
|
// le panneau paraît quand même, avec un message
|
|
@@ -838,16 +839,22 @@ import * as d3 from 'd3';
|
|
|
838
839
|
* @property {number} [smoothing=0] Elevation smoothing window, in METERS (0 = none).
|
|
839
840
|
* @property {?number} [xTicks=null] X axis ticks (null = auto from width).
|
|
840
841
|
* @property {?number} [yTicks=null] Y axis ticks (null = auto from height).
|
|
841
|
-
* @property {('auto'|number|{exaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
842
|
+
* @property {('auto'|number|{exaggeration:number}|{maxExaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
842
843
|
* profile fills the height, which is legible but changes scale from one track to the
|
|
843
844
|
* next, so a 2 % ramp looks like a wall and two profiles cannot be compared. A number
|
|
844
845
|
* fixes the metres covered per physical centimetre, which makes RANGES comparable.
|
|
845
846
|
* `{exaggeration}` fixes the ratio between the two axes instead, which makes SLOPES
|
|
846
847
|
* comparable: the gradient read off the chart is the real one, multiplied by the same
|
|
847
848
|
* factor on every track, and the control recomputes it per track and per A/B crop.
|
|
848
|
-
*
|
|
849
|
-
*
|
|
850
|
-
*
|
|
849
|
+
* `{maxExaggeration}` keeps `'auto'` — the height is filled, which reads best — and
|
|
850
|
+
* only reins in the absurd: a short, gently sloping track whose 2 % ramp would
|
|
851
|
+
* otherwise be drawn as a wall. A track already under the cap is untouched, so unlike
|
|
852
|
+
* a fixed exaggeration it never flattens a mountain traverse to fit a rule.
|
|
853
|
+
* A number or `{exaggeration}` is a **floor**, not a cage: a track whose range exceeds
|
|
854
|
+
* what the height can show would spill out of the frame, which is worse than losing
|
|
855
|
+
* comparability, so the scale then widens silently, nothing being drawn on the chart
|
|
856
|
+
* to say so. The extra room the scale asks for is added ABOVE the track, never below:
|
|
857
|
+
* centring it would push the axis under sea level on a mountain profile.
|
|
851
858
|
* @property {'click'|'mouseover'} [show='click'] How a track is selected on the map.
|
|
852
859
|
* @property {boolean} [showWithoutElevation=true] What to do with a track that ends up
|
|
853
860
|
* with no elevation at all: none in its geometry, and none the terrain model could
|
|
@@ -1507,23 +1514,44 @@ import * as d3 from 'd3';
|
|
|
1507
1514
|
// La publier partout est le seul moyen de voir la différence plutôt que d'y croire.
|
|
1508
1515
|
const rapport = (etendue) => (cmH > 0 && etendue > 0) ? (s.distance / cmH) / (etendue / cm) : null;
|
|
1509
1516
|
|
|
1510
|
-
|
|
1517
|
+
let vs = this._verticalScaleFor(s, innerW);
|
|
1511
1518
|
if (!(vs > 0)) {
|
|
1512
1519
|
// `'auto'` : la hauteur est remplie, donc c'est l'amplitude qui décide de tout.
|
|
1513
1520
|
// `nice()` arrondit le domaine vers l'extérieur, d'où la lecture APRÈS coup.
|
|
1514
1521
|
const echelle = d3.scaleLinear().domain([bas, haut]).range([innerH, 0]).nice();
|
|
1515
1522
|
const dom = echelle.domain();
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1523
|
+
const obtenu = rapport(dom[1] - dom[0]);
|
|
1524
|
+
// Un PLAFOND d'exagération, s'il en est demandé un. Remplir la hauteur est ce
|
|
1525
|
+
// qui se lit le mieux, mais sur une trace courte et peu accidentée cela dresse
|
|
1526
|
+
// une pente de 2 % en muraille. Le plafond n'intervient que là : quand le
|
|
1527
|
+
// remplissage dépasse le rapport permis, on élargit l'échelle jusqu'à lui. Une
|
|
1528
|
+
// trace assez accidentée pour rester en dessous n'est jamais aplatie, ce qu'une
|
|
1529
|
+
// exagération FIXE lui imposerait — à 680 km d'une traversée, elle n'occuperait
|
|
1530
|
+
// plus qu'un dixième du cadre.
|
|
1531
|
+
const plafond = this._plafondExageration();
|
|
1532
|
+
if (!(plafond > 0) || obtenu == null || obtenu <= plafond) {
|
|
1533
|
+
this._vScale = null; // aucune échelle absolue demandée
|
|
1534
|
+
this._vExaggeration = obtenu;
|
|
1535
|
+
return echelle;
|
|
1536
|
+
}
|
|
1537
|
+
vs = (s.distance / cmH) / plafond; // l'échelle qui donne exactement le plafond
|
|
1519
1538
|
}
|
|
1520
1539
|
const etendue = Math.max(vs * cm, haut - bas); // jamais moins qu'il n'en faut
|
|
1521
|
-
const milieu = (bas + haut) / 2;
|
|
1522
1540
|
this._vScale = etendue / cm; // m/cm effectivement appliqués
|
|
1523
1541
|
// Sous le plancher, le rapport retombe sous celui demandé : c'est la seule façon de
|
|
1524
1542
|
// savoir que c'est arrivé.
|
|
1525
1543
|
this._vExaggeration = rapport(etendue);
|
|
1526
|
-
|
|
1544
|
+
|
|
1545
|
+
// La marge que l'échelle impose se place AU-DESSUS, pas de part et d'autre.
|
|
1546
|
+
// Centrer la fenêtre creuse sous la trace : une échelle large - ce que demande
|
|
1547
|
+
// une exagération fixe sur une trace longue - fait alors descendre l'axe sous le
|
|
1548
|
+
// niveau de la mer, et on lit « -900 m » sur un profil de montagne. Le plancher
|
|
1549
|
+
// est donc zéro, ou le point le plus bas de la trace s'il passe dessous : une
|
|
1550
|
+
// dépression existe, une altitude négative inventée, non.
|
|
1551
|
+
const plancher = Math.min(0, bas);
|
|
1552
|
+
let y0 = (bas + haut) / 2 - etendue / 2; // le centrage, quand il tient
|
|
1553
|
+
if (y0 < plancher) y0 = plancher;
|
|
1554
|
+
return d3.scaleLinear().domain([y0, y0 + etendue]).range([innerH, 0]);
|
|
1527
1555
|
}
|
|
1528
1556
|
|
|
1529
1557
|
/**
|
|
@@ -1541,6 +1569,13 @@ import * as d3 from 'd3';
|
|
|
1541
1569
|
*
|
|
1542
1570
|
* @private
|
|
1543
1571
|
*/
|
|
1572
|
+
/** Le rapport à ne pas dépasser, `0` s'il n'en est pas demandé. @private */
|
|
1573
|
+
_plafondExageration() {
|
|
1574
|
+
const v = this.options.verticalScale;
|
|
1575
|
+
const n = (v && typeof v === 'object') ? Number(v.maxExaggeration) : 0;
|
|
1576
|
+
return n > 0 ? n : 0;
|
|
1577
|
+
}
|
|
1578
|
+
|
|
1544
1579
|
_verticalScaleFor(s, innerW) {
|
|
1545
1580
|
const v = this.options.verticalScale;
|
|
1546
1581
|
if (typeof v === 'number') return v;
|
|
@@ -1750,7 +1785,9 @@ import * as d3 from 'd3';
|
|
|
1750
1785
|
this._statsEl.setAttribute('title', text.join(' · '));
|
|
1751
1786
|
|
|
1752
1787
|
this._legendEl.innerHTML = '';
|
|
1753
|
-
|
|
1788
|
+
// Une légende de pentes sans altitude ne légende rien : elle annoncerait des
|
|
1789
|
+
// classes qu'aucun trait ne porte, sous un panneau qui dit n'avoir pas de profil.
|
|
1790
|
+
if (o.slope && o.slopeLegend && !sansAltimetrie) {
|
|
1754
1791
|
const sc = this._slopeScale();
|
|
1755
1792
|
for (let idx = 0; idx <= sc.maxIdx; idx++) {
|
|
1756
1793
|
const color = sc.colorByIndex(idx);
|
|
@@ -2259,6 +2296,6 @@ import * as d3 from 'd3';
|
|
|
2259
2296
|
// Stamped at build time from package.json - see rollup.config.mjs, which fails the build
|
|
2260
2297
|
// if this placeholder ever stops matching. Read from the source rather than the bundle,
|
|
2261
2298
|
// it says just that: a development copy, of no released version.
|
|
2262
|
-
ElevationProfile.version = '2.1.
|
|
2299
|
+
ElevationProfile.version = '2.1.2';
|
|
2263
2300
|
|
|
2264
2301
|
export { ElevationProfile as default };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! ol-elevation-profile 2.1.
|
|
1
|
+
/*! ol-elevation-profile 2.1.2 | MIT License | https://github.com/lc-4918/ol-elevation-profile */
|
|
2
2
|
import t from"ol/control/Control.js";import e from"ol/Overlay.js";import{unByKey as s}from"ol/Observable.js";import{toLonLat as o,transform as n,get as i,fromLonLat as l}from"ol/proj.js";import r from"ol/TileState.js";import{getDistance as a}from"ol/sphere.js";import{boundingExtent as h}from"ol/extent.js";import*as c from"d3";
|
|
3
3
|
/**
|
|
4
4
|
* Synchronized elevation profile control for OpenLayers, rendered with d3.
|
|
@@ -15,4 +15,4 @@ import t from"ol/control/Control.js";import e from"ol/Overlay.js";import{unByKey
|
|
|
15
15
|
*
|
|
16
16
|
* @module ol-elevation-profile
|
|
17
17
|
* @license MIT
|
|
18
|
-
*/const p={steelblue:{area:"#4682b4",line:"#3a6d96",axis:"#555",text:"#222",focus:"#e6550d"},lime:{area:"#9ccc2f",line:"#7da521",axis:"#555",text:"#222",focus:"#d62728"},purple:{area:"#9467bd",line:"#76529c",axis:"#555",text:"#222",focus:"#ff9f1c"},slate:{area:"#7c8a99",line:"#4a5560",axis:"#5a6570",text:"#26303a",focus:"#2f81f7"},graphite:{area:"#9a948c",line:"#5c574f",axis:"#5c574f",text:"#2b2823",focus:"#e07a3f"},amber:{area:"#f0a23b",line:"#c4671a",axis:"#7a5a36",text:"#3a2a16",focus:"#1f6fb2"}},u=["top","bottom","left","right","top-left","top-right","bottom-left","bottom-right"],d={en:{distance:"Distance",elevation:"Elevation",slope:"Slope",ascent:"D+",descent:"D-",empty:"Click a track",noElevation:"No elevation data",untitled:"Profile",time:"Time",duration:"Duration",durationUnits:{s:"sec",m:"min",h:"h",d:"d"},zoomStart:"Set start (A)",zoomEnd:"Set end (B)",zoomAll:"Show all",zoomBack:"Back one level",exportPng:"Export as PNG",collapse:"Collapse the profile",expand:"Expand the profile",loading:"Loading the elevation profile"},fr:{distance:"Distance",elevation:"Altitude",slope:"Pente",ascent:"D+",descent:"D-",empty:"Cliquez un tracé",noElevation:"Aucune altimétrie",untitled:"Profil",time:"Temps",duration:"Durée",durationUnits:{s:"sec",m:"min",h:"h",d:"j"},zoomStart:"Définir le début (A)",zoomEnd:"Définir la fin (B)",zoomAll:"Tout voir",zoomBack:"Revenir au niveau précédent",exportPng:"Exporter en PNG",collapse:"Réduire le profil",expand:"Agrandir le profil",loading:"Chargement du profil altimétrique"},es:{distance:"Distancia",elevation:"Altitud",slope:"Pendiente",ascent:"D+",descent:"D-",empty:"Haga clic en una traza",noElevation:"Sin datos de altitud",untitled:"Perfil",time:"Tiempo",duration:"Duración",durationUnits:{s:"seg",m:"min",h:"h",d:"d"},zoomStart:"Definir el inicio (A)",zoomEnd:"Definir el final (B)",zoomAll:"Ver todo",zoomBack:"Volver al nivel anterior",exportPng:"Exportar como PNG",collapse:"Contraer el perfil",expand:"Desplegar el perfil",loading:"Cargando el perfil de elevación"}},m={immersion:"docked",position:"bottom",width:520,height:180,margins:{unit:"px",top:20,right:24,bottom:30,left:48},units:"meters",dataProjection:null,dem:"terrarium",maxPoints:2e3,smoothing:0,theme:"steelblue",color:null,trackLayer:null,transparency:!1,transparencyLevel:.45,grid:!0,slope:!1,slopeClassSize:2.5,slopeColors:null,slopeSeparators:!0,slopeLegend:!0,maxClasses:8,xTicks:null,yTicks:null,verticalScale:"auto",show:"click",showWithoutElevation:!0,collapsable:!0,collapsed:!1,followMap:!0,marker:!0,hideOnMapClick:!0,responsive:!0,mobileBreakpoint:640,zoom:!1,zoomLevels:3,exportPng:!1,ignoreStops:!0,stopSpeed:.5,tooltipItems:["distance","elevation"],headerItems:["distance","ascent","descent","minmax"],titleProperty:"name",titleLink:null,lang:"en",labels:{}};function _(t,e){return f(d[t]||d.en,e||null)}function f(t,e){const s={};return Object.keys(t).forEach(e=>{s[e]=t[e]}),e&&Object.keys(e).forEach(o=>{e[o]&&"object"==typeof e[o]&&!Array.isArray(e[o])&&t[o]&&"object"==typeof t[o]?s[o]=f(t[o],e[o]):s[o]=e[o]}),s}const g=t=>String(t).replace(/[&<>"']/g,t=>({"&":"&","<":"<",">":">",'"':""","'":"'"}[t])),y=t=>"string"==typeof t&&/^(https?:)?\/\/|^mailto:/i.test(t);function x(t){if(!t||!t.getCoordinates)return[];const e=t.getCoordinates();switch(t.getType()){case"LineString":case"LinearRing":return[e];case"MultiLineString":return e;case"Polygon":return e.length?[e[0]]:[];case"MultiPolygon":return e.map(t=>t[0]).filter(Boolean);default:return[]}}function b(t,e){const s=t&&t.getProperties?t.getProperties():{};let o=s.coordTimes;null==o&&s.coordinateProperties&&(o=s.coordinateProperties.times||s.coordinateProperties.coordTimes);let n=null;if(Array.isArray(o)&&(n=Array.isArray(o[0])?o.reduce((t,e)=>t.concat(e),[]):o.slice()),!n&&e){const t=[];let s=!1;for(const o of e)for(const e of o){const o=e.length>3?e[3]:null;t.push(o),null!=o&&isFinite(o)&&(s=!0)}n=s?t:null}if(!n)return null;let i=0;const l=n.map(t=>{if(null==t||""===t)return null;const e="number"==typeof t?t>1e12?t:1e3*t:Date.parse(t);return isFinite(e)?(i++,e):null});return i>=2?l:null}function v(t,e,s){let o=t;if("function"==typeof o)try{o=o(e,s)}catch(t){return null}if(Array.isArray(o)&&(o=o[0]),o&&o.getStroke){const t=o.getStroke();if(t)return t.getColor()}return null}const S=(t,e)=>{if("imperial"===e){const e=t/1609.344;return e<.2?`${Math.round(3.28084*t)} ft`:`${e.toFixed(e<10?2:1)} mi`}return t<1e3?`${Math.round(t)} m`:`${(t/1e3).toFixed(t<1e4?2:1)} km`},M=(t,e)=>"imperial"===e?`${Math.round(3.28084*t)} ft`:`${Math.round(t)} m`;const E='<svg viewBox="0 0 24 24"><path d="M5 13h14" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round"/></svg>',k='<svg viewBox="0 0 24 24"><path d="M3 19l5-7 4 4 4-6 5 9z" fill="currentColor" opacity=".85"/></svg>',w=c.bisector(t=>t.x).left,z={terrarium:{url:"https://s3.amazonaws.com/elevation-tiles-prod/terrarium/{z}/{x}/{y}.png",encoding:"terrarium",maxZoom:14,attributions:'Elevation: <a href="https://registry.opendata.aws/terrain-tiles/">Terrain Tiles</a> (AWS Open Data)'},ign:{api:"ign",url:"https://data.geopf.fr/altimetrie/1.0/calcul/alti/rest/elevation.json",resource:"ign_rge_alti_wld",batch:200,minInterval:1100,attributions:'Elevation: <a href="https://geoservices.ign.fr/rgealti">RGE ALTI</a> (IGN)'}};function C(t){const e=Math.max(1,t.batch||200),s=t.minInterval||0;return o=>{const n=[];let i=0;const l=r=>{if(r>=o.length)return Promise.resolve(n);const a=o.slice(r,r+e),h=Math.max(0,s-(Date.now()-i));return new Promise(t=>setTimeout(t,h)).then(()=>(i=Date.now(),fetch(function(t,e){const s=t=>t.toFixed(6),o=t.url.indexOf("?")>=0?"&":"?";let n=t.url+o+"resource="+encodeURIComponent(t.resource)+"&delimiter=|&zonly=true&lon="+e.map(t=>s(t[0])).join("|")+"&lat="+e.map(t=>s(t[1])).join("|");return t.apiKey&&(n+="&"+(t.apiKeyParam||"apikey")+"="+encodeURIComponent(t.apiKey)),n}(t,a)))).then(t=>t&&t.ok?t.json():null).then(t=>{const s=t&&t.elevations;if(!Array.isArray(s)||s.length!==a.length)return null;for(const t of s)n.push(null==t||t<=-99999?null:t);return l(r+e)})};return l(0)}}const P={source:"terrarium",zoom:"auto",maxZoom:14,maxTiles:32,concurrency:6,tileSize:256},T={terrarium:(t,e,s)=>256*t+e+s/256-32768,mapbox:(t,e,s)=>.1*(65536*t+256*e+s)-1e4},A=20037508.342789244;function $(t,e){const s=t.indexOf("?")>=0?"&":"?";return t.replace(/[?&]$/,"")+s+Object.keys(e).map(t=>t+"="+encodeURIComponent(e[t])).join("&")}function L(t,e,s,o,n){const i=Object.assign({SERVICE:"WMS",REQUEST:"GetMap",VERSION:"1.3.0",FORMAT:"image/png",TRANSPARENT:"false",STYLES:""},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.WIDTH=n,i.HEIGHT=n,i.BBOX=function(t,e,s){const o=2*A/Math.pow(2,t),n=e*o-A,i=A-s*o;return[n,i-o,n+o,i]}(e,s,o).join(","),$(t.url,i)}function j(t){const e=t.olSource,s=t.band||0;return o=>{const l=e.getTileGrid&&e.getTileGrid();return(l?Promise.resolve(null):Promise.resolve(e.getView?e.getView():null)).then(a=>{const h=l||e.getTileGrid&&e.getTileGrid()||a&&a.tileGrid;if(!h)return null;const c=i(a&&a.projection||e.getProjection&&e.getProjection()||"EPSG:3857"),p=h.getResolutions?h.getResolutions().length-1:0,u=e.bandCount||1,d=o.map(t=>n([t[0],t[1]],"EPSG:4326",c)),m=h.getExtent&&h.getExtent()||a&&a.extent||null,_=t=>{const e=h.getResolution(t),s=h.getOrigin(t);let o=h.getTileSize(t);o=Array.isArray(o)?o:[o,o];const n=m?Math.round((m[2]-m[0])/e):1/0,i=m?Math.round((m[3]-m[1])/e):1/0,l=t=>Math.min(n-1,Math.max(0,t)),r=t=>Math.min(i-1,Math.max(0,t)),a=new Map,c=d.map(t=>{const n=(t[0]-s[0])/e-.5,i=(s[1]-t[1])/e-.5,h=l(Math.floor(n)),c=r(Math.floor(i));for(let t=0;t<2;t++)for(let e=0;e<2;e++){const s=Math.floor(l(h+t)/o[0]),n=Math.floor(r(c+e)/o[1]);a.set(s+"/"+n,[s,n])}return{i0:h,j0:c,tx:Math.min(1,Math.max(0,n-h)),ty:Math.min(1,Math.max(0,i-c)),clampI:l,clampJ:r}});return{res:e,origin:s,ts:o,need:a,at:c,clampI:l,clampJ:r}};let f=p,g=_(f);for(;f>0&&g.need.size>t.maxTiles;)f--,g=_(f);if(g.need.size>t.maxTiles)return null;const y=Array.from(g.need.keys());return Promise.all(y.map(t=>{const s=g.need.get(t);return(o=e.getTile(f,s[0],s[1],1,c),new Promise(t=>{const e=()=>{const e=o.getState();return e===r.LOADED?(t(o.getData?o.getData():null),!0):(e===r.ERROR||e===r.EMPTY)&&(t(null),!0)};if(e())return;const s=()=>{e()&&o.removeEventListener("change",s)};o.addEventListener("change",s),o.load&&o.load()})).then(e=>[t,e]);var o})).then(t=>{const e=new Map(t),o=(t,o)=>{const n=Math.floor(g.clampI(t)/g.ts[0]),i=Math.floor(g.clampJ(o)/g.ts[1]);t=g.clampI(t),o=g.clampJ(o);const l=e.get(n+"/"+i);if(!l)return null;const r=t-n*g.ts[0],a=l[((o-i*g.ts[1])*g.ts[0]+r)*u+s];return null!=a&&isFinite(a)?a:null};return g.at.map(t=>{const e=o(t.i0,t.j0),s=o(t.i0+1,t.j0),n=o(t.i0,t.j0+1),i=o(t.i0+1,t.j0+1);if(null==e||null==s||null==n||null==i)return null;const l=e+(s-e)*t.tx;return l+(n+(i-n)*t.tx-l)*t.ty})})})}}function B(t){const e=t.featureInfo,s=Math.max(1,t.concurrency||6);return t=>{const o=new Array(t.length);let n=0,i=!1;const r=()=>{if(i||n>=t.length)return Promise.resolve();const s=n++;return fetch(function(t,e){const s=l([e[0],e[1]]),o=t.resolution||1,n=Object.assign({SERVICE:"WMS",REQUEST:"GetFeatureInfo",VERSION:"1.3.0",INFO_FORMAT:"application/json",STYLES:"",FEATURE_COUNT:1},t.params||{}),i=0===String(n.VERSION).indexOf("1.1")?"SRS":"CRS";return delete n.SRS,delete n.CRS,n[i]=t.projection||"EPSG:3857",n.LAYERS=t.layers,n.QUERY_LAYERS=t.queryLayers||t.layers,n.WIDTH=1,n.HEIGHT=1,n.I=0,n.J=0,n.X=0,n.Y=0,n.BBOX=[s[0]-o,s[1]-o,s[0]+o,s[1]+o].join(","),$(t.url,n)}(e,t[s])).then(t=>t&&t.ok?t.json():null).then(t=>(o[s]=function(t,e){const s=t&&t.features&&t.features[0],o=s&&s.properties;if(!o)return null;if(e){const t=Number(o[e]);return isFinite(t)?t:null}for(const t of Object.keys(o)){const e=Number(o[t]);if(null!==o[t]&&""!==o[t]&&isFinite(e))return e}return null}(t,e.property),r())).catch(()=>{i=!0})},a=[];for(let e=0;e<Math.min(s,t.length);e++)a.push(r());return Promise.all(a).then(()=>i?null:o)}}class F{constructor(t){this.cfg=t,this.decode="function"==typeof t.encoding?t.encoding:T[t.encoding]||T.terrarium,this.tileUrl=function(t){const e=t.olSource;if(e&&"function"==typeof e.getTileUrlFunction){const t=e.getTileUrlFunction(),s=i("EPSG:3857");return(e,o,n)=>t([e,o,n],1,s)}return t.wms?(e,s,o)=>L(t.wms,e,s,o,t.tileSize):(e,s,o)=>t.url.replace("{z}",e).replace("{x}",s).replace("{y}",o)}(t),this.tiles=new Map}_neighbours(t,e,s){const o=function(t,e,s,o){const n=o*Math.pow(2,s),i=Math.sin(e*Math.PI/180);return[(t+180)/360*n,(.5-Math.log((1+i)/(1-i))/(4*Math.PI))*n]}(t,e,s,this.cfg.tileSize),n=o[0]-.5,i=o[1]-.5,l=Math.floor(n),r=Math.floor(i);return{i0:l,j0:r,tx:n-l,ty:i-r}}_key(t,e,s){const o=this.cfg.tileSize,n=o*Math.pow(2,s),i=Math.min(n-1,Math.max(0,e)),l=(t%n+n)%n;return{key:s+"/"+Math.floor(l/o)+"/"+Math.floor(i/o),ii:l,jj:i}}_at(t,e,s){const o=this.cfg.tileSize,n=this._key(t,e,s),i=this.tiles.get(n.key);if(!i)return null;const l=4*(n.jj%o*o+n.ii%o),r=this.decode(i[l],i[l+1],i[l+2],i[l+3]);return null!=r&&isFinite(r)?r:null}sample(t,e,s){const o=this._neighbours(t,e,s),n=this._at(o.i0,o.j0,s),i=this._at(o.i0+1,o.j0,s),l=this._at(o.i0,o.j0+1,s),r=this._at(o.i0+1,o.j0+1,s);if(null==n||null==i||null==l||null==r)return null;const a=n+(i-n)*o.tx;return a+(l+(r-l)*o.tx-a)*o.ty}tilesFor(t,e){const s=new Set;for(const o of t){const t=this._neighbours(o[0],o[1],e);for(let o=0;o<2;o++)for(let n=0;n<2;n++)s.add(this._key(t.i0+o,t.j0+n,e).key)}return s}_fetch(t){const e=t.split("/"),s=this.tileUrl(+e[0],+e[1],+e[2]);return new Promise(t=>{const e=new Image;e.crossOrigin="anonymous",e.onload=()=>{try{const s=this.cfg.tileSize,o=document.createElement("canvas");o.width=s,o.height=s;const n=o.getContext("2d",{willReadFrequently:!0});n.drawImage(e,0,0,s,s),t(n.getImageData(0,0,s,s).data)}catch(e){t(null)}},e.onerror=()=>t(null),e.src=s})}load(t){const e=Array.from(t).filter(t=>!this.tiles.has(t));let s=0,o=!0;const n=()=>{if(s>=e.length)return Promise.resolve();const t=e[s++];return this._fetch(t).then(e=>(this.tiles.set(t,e),e||(o=!1),n()))},i=[];for(let t=0;t<Math.min(this.cfg.concurrency,e.length);t++)i.push(n());return Promise.all(i).then(()=>o)}}class R extends t{constructor(t){const e=f(m,t||{});-1===u.indexOf(e.position)&&(e.position="bottom");const s=e.labels;e.labels=_(e.lang,s);const o=function(t){const e=document.createElement("div");return e.className=`ol-elevation-profile ol-unselectable ol-control oep-pos-${t.position} oep-theme-${"string"==typeof t.theme?t.theme:"custom"}`+("floating"===t.immersion?" oep-floating":""),e}(e);super({element:o,target:t&&t.target}),this.options=e,this._userLabels=s,this.slopeColors=e.slopeColors||null,this._feature=null,this._fullSamples=null,this._fullStats=null,this._samples=null,this._stats=null,this._marker=null,this._collapsed=!!e.collapsed,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._demZ=null,this._demFor=null,this._demSeq=0,this._demLoading=!1,this._trackLines=null,this._linesFor=null,this._onResize=()=>{this._feature&&!this._collapsed&&this._render()},this._buildDom(o),o.style.display="none"}get _cropMode(){return this._crops.length>0}get _cropDepth(){return this._crops.length}get _cropMax(){const t=this.options.zoomLevels;return null==t?3:Math.max(1,0|t)}static featureHasZ(t){const e=t&&t.getGeometry&&t.getGeometry();if(!e)return!1;for(const t of x(e))for(const e of t)if(e.length>2&&isFinite(e[2]))return!0;return!1}static featureHasTime(t){const e=t&&t.getGeometry&&t.getGeometry();return!!e&&!!b(t,x(e))}_buildDom(t){const e=this.options;this._applyTheme(),this._applyTransparency();const s=document.createElement("div");s.className="oep-header",this._titleEl=document.createElement("span"),this._titleEl.className="oep-title",this._titleEl.textContent=e.labels.empty,this._statsEl=document.createElement("span"),this._statsEl.className="oep-stats",s.appendChild(this._titleEl),s.appendChild(this._statsEl),this._toolbar=document.createElement("span"),this._toolbar.className="oep-toolbar";const o=(t,e,s,o)=>{const n=document.createElement("button");return n.type="button",n.className=`oep-tbtn ${t}`,n.innerHTML=e,n.title=s,n.setAttribute("aria-label",s),n.addEventListener("click",o),this._toolbar.appendChild(n),n};this._btnA=o("oep-a",'<svg viewBox="0 0 24 24"><path d="M7 5v14M11 12h8m0 0-3-3m3 3-3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomStart,()=>this._arm("A")),this._btnB=o("oep-b",'<svg viewBox="0 0 24 24"><path d="M17 5v14M13 12H5m0 0 3-3m-3 3 3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomEnd,()=>this._arm("B")),this._btnBack=o("oep-back",'<svg viewBox="0 0 24 24"><path d="M10 6 4 12l6 6M4 12h10a6 6 0 0 1 6 6" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomBack,()=>this._popCrop()),this._btnAll=o("oep-all",'<svg viewBox="0 0 24 24"><path d="M4 12h16M4 12l4-4M4 12l4 4M20 12l-4-4M20 12l-4 4" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomAll,()=>this._exitZoom()),this._btnPng=o("oep-png",'<svg viewBox="0 0 24 24"><path d="M12 4v10m0 0 4-4m-4 4-4-4M5 18h14" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.exportPng,()=>this.exportPNG()),s.appendChild(this._toolbar);const n=document.createElement("button");n.className="oep-toggle",n.type="button",n.innerHTML=this._collapsed?k:E,n.addEventListener("click",()=>this.toggleCollapsed()),s.appendChild(n),this._toggleBtn=n,this._applyToggleLabel(),this._legendEl=document.createElement("div"),this._legendEl.className="oep-legend",this._legendEl.style.display="none",this._body=document.createElement("div"),this._body.className="oep-body",t.appendChild(s),t.appendChild(this._legendEl),t.appendChild(this._body),this._applyCollapsable(),this._updateZoomButtons(),this._collapsed&&t.classList.add("oep-collapsed")}_applyLabels(){const t=this.options.labels,e=(t,e)=>{t&&e&&(t.title=e,t.setAttribute("aria-label",e))};e(this._btnA,t.zoomStart),e(this._btnB,t.zoomEnd),e(this._btnBack,t.zoomBack),e(this._btnAll,t.zoomAll),e(this._btnPng,t.exportPng),this._applyToggleLabel(),this._titleEl&&!this._feature&&(this._titleEl.textContent=t.empty)}_applyToggleLabel(){const t=this.options.labels,e=this._collapsed?t.expand:t.collapse;this._toggleBtn&&e&&(this._toggleBtn.title=e,this._toggleBtn.setAttribute("aria-label",e))}_resolveColor(){const t=this.options;return t.color?"auto"===t.color?this._featureColor():t.color:null}_featureColor(){const t=this._feature;if(!t)return null;const e=this.getMap()?this.getMap().getView().getResolution():1;let s=v(t.getStyle&&t.getStyle(),t,e);return!s&&this.options.trackLayer&&(s=v(this.options.trackLayer.getStyle&&this.options.trackLayer.getStyle(),t,e)),function(t){if(null==t)return null;if("string"==typeof t)return t;if(Array.isArray(t)){const e=t.length>3?t[3]:1;return`rgba(${0|t[0]},${0|t[1]},${0|t[2]},${e})`}return null}(s)}_applyTheme(){const t=this.options,e="object"==typeof t.theme?t.theme:p[t.theme]||p.steelblue;this.themeColors=e;const s=this.element,o=this._resolveColor(),n=o||e.area;let i=e.line;if(o)try{i=String(c.color(o).darker(.7))}catch(t){i=o}s.style.setProperty("--oep-area",n),s.style.setProperty("--oep-line",i),s.style.setProperty("--oep-axis",e.axis),s.style.setProperty("--oep-text",e.text),s.style.setProperty("--oep-focus",e.focus)}_applyTransparency(){const t=this.options.transparency;let e;e=!1===t||null==t?1:!0===t?this.options.transparencyLevel:Math.max(0,Math.min(1,+t)),this.element.style.setProperty("--oep-bg",`rgba(255,255,255,${e})`),this.element.classList.toggle("oep-transparent",e<1)}_applyCollapsable(){const t=this.options.collapsable;this._toggleBtn.style.display=t?"":"none",!t&&this._collapsed&&this.toggleCollapsed(!1)}toggleCollapsed(t){this._collapsed="boolean"==typeof t?t:!this._collapsed,this.element.classList.toggle("oep-collapsed",this._collapsed),this._toggleBtn.innerHTML=this._collapsed?k:E,this._applyToggleLabel(),!this._collapsed&&this._feature&&this._render(),this._adjustAttribution()}_availWidth(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement();return e&&e.clientWidth||("undefined"!=typeof window?window.innerWidth:1024)}_isMobile(){return this.options.responsive&&"undefined"!=typeof window&&window.innerWidth<=(this.options.mobileBreakpoint||640)}_applyPlacement(){const t=this._isMobile();let e=this.options.position;return t&&(e=/top/.test(e)?"top":"bottom"),this.element.className=this.element.className.replace(/oep-pos-\S+/,`oep-pos-${e}`),this.element.classList.toggle("oep-mobile",t),t}_adjustAttribution(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement(),s=e&&e.querySelector&&e.querySelector(".ol-attribution");if(!s)return;if(s.style.bottom="",s.style.right="","none"===this.element.style.display||this._collapsed)return;const o=e.getBoundingClientRect(),n=this.element.getBoundingClientRect();if(!n.height)return;const i=o.bottom-n.bottom,l=o.right-n.right;i<n.height&&l<24&&(s.style.right=`${Math.max(0,Math.round(l))}px`,s.style.bottom=`${Math.round(n.height+2*i)}px`)}setMap(t){const o=this.getMap();if(super.setMap(t),this._mapKeys&&(this._mapKeys.forEach(s),this._mapKeys=null),o&&"undefined"!=typeof window&&window.removeEventListener("resize",this._onResize),this._marker&&!t&&this._marker.setPosition(void 0),!t)return;const n=this.options;if(n.dataProjection||(n.dataProjection=t.getView().getProjection()),n.marker&&!this._marker){const s=document.createElement("div");s.className="oep-marker",this._marker=new e({element:s,positioning:"center-center",stopEvent:!1}),t.addOverlay(this._marker)}"undefined"!=typeof window&&window.addEventListener("resize",this._onResize);const i=e=>t.forEachFeatureAtPixel(e,t=>{const e=t.getGeometry();return(s=e)&&/^(Multi)?(LineString|Polygon)$|^LinearRing$/.test(s.getType())?t:void 0;var s});this._mapKeys=[],this._mapKeys.push(t.on("click",t=>{const e=i(t.pixel);"mouseover"!==this.options.show&&e&&e!==this._feature&&this.setFeature(e),this.options.hideOnMapClick&&!e&&this._feature&&this.clear()})),this._mapKeys.push(t.on("pointermove",e=>{if("mouseover"===this.options.show){const t=i(e.pixel);t&&t!==this._feature&&this.setFeature(t)}if(!this.options.followMap||!this._feature||this._collapsed)return;const s=this._closestOnProfile(e.coordinate);if(!s)return;const o=t.getPixelFromCoordinate(s);o&&(Math.hypot(o[0]-e.pixel[0],o[1]-e.pixel[1])<14?this._focusByCoord(s):this._clearFocus())})),this._mapKeys.push(t.on("moveend",()=>{const e=this._crops[this._crops.length-1];e&&e.fitRes&&t.getView().getResolution()>1.25*e.fitRes&&this._popCrop()})),this._mapKeys.push(t.on("change:size",this._onResize))}setFeature(t){return this._feature=t||null,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,t?(this.element.style.display="",this._compute(),this._fillFromDem(t),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render(),this):(this._fullSamples=this._samples=null,this._demZ=this._demFor=null,this._trackLines=this._linesFor=null,this._clear(),this)}clear(){return this.setFeature(null)}getStats(){return this._stats}setTheme(t){return this.options.theme=t,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setColor(t){return this.options.color=t||null,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setOptions(t){return this.options=f(this.options,t||{}),t&&"slopeColors"in t&&(this.slopeColors=t.slopeColors||null),t&&(t.theme||"color"in t)&&this._applyTheme(),t&&("transparency"in t||"transparencyLevel"in t)&&this._applyTransparency(),t&&"collapsable"in t&&this._applyCollapsable(),t&&"labels"in t&&(this._userLabels=f(this._userLabels||{},t.labels)),t&&("lang"in t||"labels"in t)&&(this.options.labels=_(this.options.lang,this._userLabels),this._applyLabels()),t&&("zoom"in t||"exportPng"in t)&&this._updateZoomButtons(),t&&void 0!==t.width&&"number"==typeof t.width&&(this.options.width=t.width),t&&"dem"in t&&(this._demZ=null,this._demFor=null,this._trackLines=null,this._linesFor=null),this._feature&&(this._compute(),this._fillFromDem(this._feature),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render()),this}_fillFromDem(t){const e=function(t){if(!t)return null;if("function"==typeof t)return Object.assign({},P,{sample:t});const e=!0===t||"string"==typeof t?{source:!0===t?"terrarium":t}:Object.assign({},t);if("function"==typeof e.sample)return Object.assign({},P,e);if(e.track){const t=Object.assign({},P,e);return t.track=Object.assign({coords:"coords",parse:null,fetchOptions:null},"string"==typeof e.track?{url:e.track}:e.track),t.track.url?t:null}if(e.featureInfo){const t=Object.assign({},P,e);return t.sample=B(t),t}if(e.olSource&&"function"!=typeof e.olSource.getTileUrlFunction&&"function"==typeof e.olSource.getTile){const t=Object.assign({},P,e);return t.sample=j(t),t}const s=e.url||e.wms||e.olSource,o=z[e.source]||(s?{}:z.terrarium),n=Object.assign({},P,o,e);return"ign"===n.api?(n.sample=C(n),n):n.url||n.wms||n.olSource?n:null}(this.options.dem);if(!e||!t||this._demFor===t||this._linesFor===t)return;if(R.featureHasZ(t))return;if(!e.sample&&("undefined"==typeof Image||"undefined"==typeof document))return;const s=t.getGeometry&&t.getGeometry(),n=s?x(s):[],i=this.options.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=[];for(const t of n)for(const e of t)l.push(o(e,i));if(!l.length&&!e.track)return;const r=++this._demSeq;this._demLoading=!0;try{this._startFill(e,r,t,l,i)}catch(e){this._demDone(r,t,null,l.length,null,0)}}_startFill(t,e,s,o,n){if(t.track)return void this._startTrackFill(t,e,s,o.length,n);if(t.sample)return void Promise.resolve().then(()=>t.sample(o,{feature:s,projection:n})).then(t=>this._demDone(e,s,t,o.length,null,0)).catch(()=>this._demDone(e,s,null,o.length,null,0));const i=new F(t),l=function(t,e,s){if("number"==typeof s.zoom)return s.zoom;for(let o=s.maxZoom;o>0;o--)if(t.tilesFor(e,o).size<=s.maxTiles)return o;return 1}(i,o,t);i.load(i.tilesFor(o,l)).then(t=>{const n=t?o.map(t=>i.sample(t[0],t[1],l)):null;this._demDone(e,s,n,o.length,l,i.tiles.size)}).catch(()=>this._demDone(e,s,null,o.length,l,0))}_startTrackFill(t,e,s,o,n){const i=function(t,e){if("function"==typeof t)return t(e)||null;if("string"!=typeof t||!e)return null;let s=!0;const o=t.replace(/\{(\w+)\}/g,(t,o)=>{const n=e.get(o);return null==n||""===n?(s=!1,""):encodeURIComponent(String(n))});return s?o:null}(t.track.url,s);i?Promise.resolve().then(()=>fetch(i,t.track.fetchOptions||void 0)).then(t=>{if(!t.ok)throw new Error(String(t.status));return t.json()}).then(i=>{const l=t.track.parse?t.track.parse(i,s):Array.isArray(i)?i:i&&i[t.track.coords];this._trackDone(e,s,l,o,n)}).catch(()=>this._demDone(e,s,null,o,null,0)):this._demDone(e,s,null,o,null,0)}_trackDone(t,e,s,o,i){const l=()=>this._demDone(t,e,null,o,null,0);if(!Array.isArray(s)||!s.length)return l();if("number"==typeof s[0])return void this._demDone(t,e,s,o,null,0);if(t!==this._demSeq||this._feature!==e)return;const r=t=>null!=t&&isFinite(t),a=[];for(const t of s){if(!t||t.length<3||!r(t[0])||!r(t[1])||!r(t[2]))return l();const e=n([t[0],t[1]],"EPSG:4326",i);a.push([e[0],e[1],t[2]])}if(a.length<2)return l();this._demLoading=!1,this._trackLines=[a],this._linesFor=e,this._demZ=null,this._demFor=null,this._compute(),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:!0,zoom:null,tiles:0})}_demDone(t,e,s,o,n,i){if(t!==this._demSeq||this._feature!==e)return;const l=Array.isArray(s)&&s.length===o&&s.every(t=>null!=t&&isFinite(t));this._demLoading=!1,l&&(this._demZ=s,this._demFor=e,this._compute()),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:l,zoom:n,tiles:i})}_compute(){const t=this.options,e=this._linesFor===this._feature&&this._trackLines,s=this._feature.getGeometry&&this._feature.getGeometry(),n=e?this._trackLines:s?x(s):[],i=t.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=this._demFor===this._feature?this._demZ:null,r=e?null:b(this._feature,n);this._hasTime=!!r;const h=!1!==t.ignoreStops,c=null!=t.stopSpeed?t.stopSpeed:.5,p=[];let u=0,d=null,m=-1,_=0,f=null;for(const t of n)for(const e of t){m++;const t=o(e,i);let s=0;d&&(s=a(d,t),u+=s);let n=null;if(r&&null!=r[m]){const t=r[m];if(null!=f){const e=(t-f)/1e3;e>0&&(!h||s/e>=c)&&(_+=e)}n=_,f=t}d=t;const g=e.length>2&&isFinite(e[2])?e[2]:l?l[m]:0;p.push({x:u,z:g,coord:e,t:n})}t.smoothing>0&&this._smooth(p,t.smoothing);const g=this._decimate(p,t.maxPoints);this._addSlope(g),this._fullSamples=g,this._fullStats=this._statsOf(g,!0),this._applyCrops()}_pxPerCm(){try{const t=document.createElement("div");t.style.cssText="position:absolute;left:-9999px;top:0;width:1cm;height:1cm",(this.element||document.body).appendChild(t);const e=t.getBoundingClientRect().height;if(t.remove(),e>0)return e}catch(t){}return 96/2.54}_yScale(t,e,s,o){const n=t.min-e,i=t.max+e,l=s/this._pxPerCm(),r=o/this._pxPerCm(),a=e=>r>0&&e>0?t.distance/r/(e/l):null,h=this._verticalScaleFor(t,o);if(!(h>0)){const t=c.scaleLinear().domain([n,i]).range([s,0]).nice(),e=t.domain();return this._vScale=null,this._vExaggeration=a(e[1]-e[0]),t}const p=Math.max(h*l,i-n),u=(n+i)/2;return this._vScale=p/l,this._vExaggeration=a(p),c.scaleLinear().domain([u-p/2,u+p/2]).range([s,0])}_verticalScaleFor(t,e){const s=this.options.verticalScale;if("number"==typeof s)return s;const o=s&&"object"==typeof s?Number(s.exaggeration):0;if(!(o>0&&t.distance>0&&e>0))return 0;const n=e/this._pxPerCm();return t.distance/n/o}_statsOf(t,e){let s=0,o=0,n=1/0,i=-1/0,l=0;for(let e=0;e<t.length;e++){const r=t[e].z;if(r<n&&(n=r),r>i&&(i=r),e>0){const n=r-t[e-1].z;n>0?s+=n:o-=n}const a=Math.abs(t[e].slope||0);a>l&&(l=a)}const r=t.length?t[t.length-1].x-t[0].x:0,a=t.length?t[0].t:null,h=t.length?t[t.length-1].t:null;return{distance:r,duration:null!=a&&null!=h?h-a:null,ascent:s,descent:o,min:isFinite(n)?n:0,max:isFinite(i)?i:0,maxAbsSlope:l,points:t.length}}_smooth(t,e){if(!(e>0)||t.length<3)return;const s=e/2,o=t.map(t=>t.z);let n=0,i=0,l=0;for(let e=0;e<t.length;e++){const r=t[e].x;for(;n<t.length&&t[n].x<r-s;)l-=o[n],n++;for(;i<t.length&&t[i].x<=r+s;)l+=o[i],i++;t[e].z=i>n?l/(i-n):o[e]}}_decimate(t,e){const s=t=>({x:t.x,z:t.z,coord:t.coord,t:t.t});if(!e||t.length<=e)return t.map(s);const o=t.length/e,n=[];for(let i=0;i<e;i++)n.push(s(t[Math.floor(i*o)]));return n.push(s(t[t.length-1])),n}_addSlope(t){for(let e=1;e<t.length;e++){const s=t[e].x-t[e-1].x;t[e].slope=s>0?(t[e].z-t[e-1].z)/s*100:0}t.length&&(t[0].slope=t.length>1?t[1].slope:0)}_slopeScale(){const t=this.options.slopeClassSize||2.5,e=this.options.maxClasses||8,s=Math.max(1,Math.floor((this._stats.maxAbsSlope||0)/t)),o=Math.min(s,e-1),n=s>o;let i;if(this.slopeColors&&this.slopeColors.length){const t=c.interpolateRgbBasis(this.slopeColors);i=e=>t(o?e/o:0)}else{const t=c.scaleLinear().domain([0,.16,.42,.68,1]).range(["#2166ac","#27a35a","#ffe000","#f4791f","#d7191c"]).interpolate(c.interpolateRgb).clamp(!0);i=e=>String(t(o?e/o:0))}return{classSize:t,maxIdx:o,capped:n,colorByIndex:i}}_classIndex(t,e){return Math.min(e.maxIdx,Math.floor(Math.abs(t)/e.classSize))}_fmtDuration(t){if(null==t||!isFinite(t))return"";const e=this.options.labels&&this.options.labels.durationUnits||d.en.durationUnits;if((t=Math.max(0,Math.round(t)))<60)return t+" "+e.s;if(t<3600)return Math.round(t/60)+" "+e.m;if(t<86400){let s=Math.floor(t/3600),o=Math.round(t%3600/60);return 60===o&&(s++,o=0),o?`${s} ${e.h} ${o} ${e.m}`:`${s} ${e.h}`}let s=Math.floor(t/86400),o=Math.round(t%86400/3600);return 24===o&&(s++,o=0),o?`${s} ${e.d} ${o} ${e.h}`:`${s} ${e.d}`}_hasElevation(){const t=this._feature;return!!t&&(!!R.featureHasZ(t)||(!(this._demFor!==t||!this._demZ)||!(this._linesFor!==t||!this._trackLines)))}_renderNoElevation(){if(!this.options.showWithoutElevation)return void(this.element.style.display="none");this.element.style.display="",this._applyTheme(),this._applyPlacement(),this._renderHeader(!0);const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-noelev",e.style.height=`${t}px`,e.setAttribute("role","status"),e.textContent=this.options.labels.noElevation,this._body.appendChild(e),this._clearFocus()}_pickProperty(t,e,s){if(!e||!t||!t.get)return null;for(const o of Array.isArray(e)?e:[e]){const e=t.get(o);if(null!=e&&""!==e&&(!s||s(e)))return e}return null}_renderTitle(){const t=this.options,e=this._feature;if(!e)return;const s=this._pickProperty(e,t.titleProperty)||t.labels.untitled,o=this._pickProperty(e,t.titleLink,y);y(o)?this._titleEl.innerHTML=`<a href="${g(o)}" target="_blank" rel="noopener">${g(s)}</a>`:this._titleEl.textContent=s,this._titleEl.setAttribute("title",s)}_renderHeader(t){const e=this.options,s=this._stats,o=this._feature;if(this._renderTitle(),this._demLoading)return this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._legendEl.innerHTML="",void(this._legendEl.style.display="none");const n=[],i=[];if(e.headerItems.forEach(l=>{if("string"==typeof l){if(t&&("ascent"===l||"descent"===l||"min"===l||"max"===l||"minmax"===l))return;if("distance"===l){if(!(s&&s.distance>0))return;n.push(`<b>${S(s.distance,e.units)}</b>`),i.push(S(s.distance,e.units))}else if("ascent"===l)n.push(`<span class="oep-up">${e.labels.ascent} ${M(s.ascent,e.units)}</span>`),i.push(`${e.labels.ascent} ${M(s.ascent,e.units)}`);else if("descent"===l)n.push(`<span class="oep-down">${e.labels.descent} ${M(s.descent,e.units)}</span>`),i.push(`${e.labels.descent} ${M(s.descent,e.units)}`);else if("min"===l)n.push(M(s.min,e.units)),i.push(M(s.min,e.units));else if("max"===l)n.push(M(s.max,e.units)),i.push(M(s.max,e.units));else if("minmax"===l){const t=`${M(s.min,e.units)}-${M(s.max,e.units)}`;n.push(t),i.push(t)}else if("duration"===l&&null!=s.duration){const t=this._fmtDuration(s.duration);n.push(`<span class="oep-time">${g(e.labels.duration)} ${t}</span>`),i.push(`${e.labels.duration} ${t}`)}}else if(l&&l.property){const t=o.get&&o.get(l.property);if(null==t||""===t)return;const e=l.label?`${l.label} `:"";l.asLink&&y(t)?(n.push(`${e}<a href="${g(t)}" target="_blank" rel="noopener">${g(l.linkText||l.label||t)}</a>`),i.push(`${l.label||""} ${t}`)):(n.push(g(e+t)),i.push(e+t))}}),this._statsEl.innerHTML=n.join(" · "),this._statsEl.setAttribute("title",i.join(" · ")),this._legendEl.innerHTML="",e.slope&&e.slopeLegend){const t=this._slopeScale();for(let e=0;e<=t.maxIdx;e++){const s=t.colorByIndex(e),o=t.capped&&e===t.maxIdx?`≥ ${e*t.classSize} %`:`${e*t.classSize}-${(e+1)*t.classSize} %`,n=document.createElement("span");n.className="oep-leg-it",n.innerHTML=`<i class="oep-sw" style="background:${s}"></i>${o}`,this._legendEl.appendChild(n)}this._legendEl.style.display=""}else this._legendEl.style.display="none"}_renderSpinner(){const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-loading",e.style.height=`${t}px`,e.setAttribute("role","status"),e.setAttribute("aria-label",this.options.labels.loading);const s=document.createElement("div");s.className="oep-spinner",e.appendChild(s),this._body.appendChild(e)}_render(){const t=this.options,e=this._stats,s=this._samples;if(!this._demLoading&&!this._hasElevation())return void this._renderNoElevation();if(!s||!s.length)return;this._applyTheme();const o=this._applyPlacement();if(this._renderHeader(),this._demLoading)return void this._renderSpinner();const n=t.margins,i=n.unit||"px",l=t=>"px"===i?t:t*(parseFloat(getComputedStyle(this.element).fontSize)||16),r=this._availWidth(),a="auto"===t.width||"100%"===t.width||"full"===t.width?r:Math.min("number"==typeof t.width?t.width:parseFloat(t.width)||r,r);this.element.style.width=o?"":`${a}px`;const h=this.element.clientWidth||(o?r:a),p=Math.max(220,h-16),u="number"==typeof t.height?t.height:180,d=l(n.top),m=l(n.right),_=l(n.bottom),f=l(n.left),g=Math.max(10,p-f-m),y=Math.max(10,u-d-_),x=null!=t.xTicks?t.xTicks:Math.max(2,Math.round(g/80)),b=null!=t.yTicks?t.yTicks:Math.max(2,Math.round(y/40));this._body.innerHTML="";const v=c.select(this._body).append("svg").attr("class","oep-svg").attr("width",p).attr("height",u).attr("viewBox",`0 0 ${p} ${u}`),S=v.append("g").attr("transform",`translate(${f},${d})`),M=c.scaleLinear().domain([0,e.distance]).range([0,g]),E=.1*(e.max-e.min)||10,k=this._yScale(e,E,y,g);this._x=M,this._y=k,this._dims={innerW:g,innerH:y},t.grid&&S.append("g").attr("class","oep-grid").call(c.axisLeft(k).ticks(b).tickSize(-g).tickFormat(""));const w="imperial"===t.units?1609.344:1e3;const z=c.area().x(t=>M(t.x)).y0(y).y1(t=>k(t.z));if(t.slope){const e=this._slopeScale(),o=[];let n=1;for(;n<s.length;){const t=this._classIndex(s[n].slope,e);let i=n;for(;i+1<s.length&&this._classIndex(s[i+1].slope,e)===t;)i++;S.append("path").datum(s.slice(n-1,i+1)).attr("class","oep-area-slope").attr("fill",e.colorByIndex(t)).attr("d",z),n>1&&o.push(s[n-1]),n=i+1}t.slopeSeparators&&o.forEach(t=>{S.append("line").attr("class","oep-slope-sep").attr("x1",M(t.x)).attr("x2",M(t.x)).attr("y1",k(t.z)).attr("y2",y)})}else S.append("path").datum(s).attr("class","oep-area").attr("d",z);S.append("path").datum(s).attr("class","oep-line").attr("d",c.line().x(t=>M(t.x)).y(t=>k(t.z))),S.append("g").attr("class","oep-axis oep-axis-x").attr("transform",`translate(0,${y})`).call(c.axisBottom(M).ticks(x).tickFormat(t=>(t/w).toFixed(t/w<10?1:0))),S.append("text").attr("class","oep-axis-label").attr("x",g).attr("y",y+_-4).attr("text-anchor","end").text((t=>"imperial"===t?"mi":"km")(t.units)),S.append("g").attr("class","oep-axis oep-axis-y").call(c.axisLeft(k).ticks(b).tickFormat(e=>"imperial"===t.units?Math.round(3.28084*e):e)),t.zoom&&this._cropDepth<this._cropMax&&[["A",this._zoomA],["B",this._zoomB]].forEach(([t,e])=>{if(null==e)return;const s=M(e);S.append("line").attr("class","oep-ab-line").attr("x1",s).attr("x2",s).attr("y1",0).attr("y2",y),S.append("text").attr("class","oep-ab-label").attr("x",s).attr("y",-6).attr("text-anchor","middle").text(t)});const C=S.append("g").attr("class","oep-focus").style("display","none");C.append("line").attr("class","oep-focus-line").attr("y1",0).attr("y2",y),C.append("circle").attr("class","oep-focus-dot").attr("r",4);const P=C.append("g").attr("class","oep-focus-label");P.append("rect").attr("class","oep-focus-bg"),P.append("text").attr("class","oep-focus-txt"),this._focus=C;const T=t=>{const s=c.pointer(t,S.node())[0];return Math.max(0,Math.min(e.distance,M.invert(s)))},A=v.append("rect").attr("class","oep-overlay").attr("x",f).attr("y",d).attr("width",g).attr("height",y);A.on("mousemove",t=>{const e=this._sampleAt(T(t));e&&(this._setFocus(e),this._marker&&this._marker.setPosition(e.coord))}).on("mouseout",()=>this._clearFocus()),A.on("click",t=>this._placeBound(T(t))),this._armed&&A.style("cursor","col-resize"),this._adjustAttribution()}static get _EXPORT_PROPS(){return["fill","fill-opacity","stroke","stroke-width","stroke-dasharray","stroke-linecap","stroke-linejoin","opacity","font-family","font-size","font-weight","text-anchor","shape-rendering"]}_freezeStyles(t,e){const s=R._EXPORT_PROPS,o=getComputedStyle(t);let n="";for(const t of s){const e=o.getPropertyValue(t);e&&(n+=`${t}:${e};`)}e.setAttribute("style",n);const i=t.children,l=e.children;for(let t=0;t<i.length&&t<l.length;t++)this._freezeStyles(i[t],l[t])}_exportSvg(){const t=this._body.querySelector("svg");if(!t)return null;const e=getComputedStyle(this.element),s=e.getPropertyValue("--oep-bg").trim()||"#fff",o=e.getPropertyValue("--oep-text").trim()||"#222",n=e.fontFamily||"system-ui, sans-serif",i=+t.getAttribute("width"),l=+t.getAttribute("height"),r=this._statsEl.textContent?15:0,a="none"!==this._legendEl.style.display?this._legendEl:null,h=28+r+(a?18:0),c=t.cloneNode(!0);c.querySelectorAll(".oep-focus, .oep-overlay").forEach(t=>t.remove()),this._freezeStyles(t,c);const p=t=>g(String(t)),u=[];if(u.push(`<rect width="${i+16}" height="${l+h+8}" fill="${p(s)}"/>`),u.push(`<text x="8" y="21" style="font-family:${p(n)};font-size:13px;font-weight:600;fill:${p(o)}">${p(this._titleEl.textContent)}</text>`),r&&u.push(`<text x="8" y="38" style="font-family:${p(n)};font-size:11px;fill:${p(o)};opacity:.85">${p(this._statsEl.textContent)}</text>`),a){let t=8;const e=28+r+12;for(const s of a.querySelectorAll(".oep-leg-it")){const i=s.querySelector(".oep-sw"),l=i?getComputedStyle(i).backgroundColor:"none",r=s.textContent.trim();u.push(`<rect x="${t}" y="${e-8}" width="10" height="10" fill="${p(l)}"/>`),u.push(`<text x="${t+14}" y="${e}" style="font-family:${p(n)};font-size:10px;fill:${p(o)}">${p(r)}</text>`),t+=14+5.6*r.length+10}}return u.push(`<g transform="translate(8,${h})">${(new XMLSerializer).serializeToString(c)}</g>`),{width:i+16,height:l+h+8,svg:`<svg xmlns="http://www.w3.org/2000/svg" width="${i+16}" height="${l+h+8}" viewBox="0 0 ${i+16} ${l+h+8}">${u.join("")}</svg>`}}exportPNG(t){const e=t||{},s=this._exportSvg();if(!s)return Promise.reject(new Error("ol-elevation-profile: nothing to export"));const o=e.scale||"undefined"!=typeof window&&window.devicePixelRatio||1;return new Promise((t,n)=>{const i=new Image;i.onload=()=>{try{const l=document.createElement("canvas");l.width=Math.round(s.width*o),l.height=Math.round(s.height*o);const r=l.getContext("2d");r.scale(o,o),r.drawImage(i,0,0),l.toBlob(s=>{s?(!1!==e.download&&this._save(s,e.filename),t(s)):n(new Error("ol-elevation-profile: PNG encoding failed"))},"image/png")}catch(t){n(t)}},i.onerror=()=>n(new Error("ol-elevation-profile: SVG could not be rasterised")),i.src="data:image/svg+xml;charset=utf-8,"+encodeURIComponent(s.svg)})}_save(t,e){const s=e||`${(this._titleEl.textContent||"profile").replace(/[\\/:*?"<>|]+/g,"-").trim()}.png`,o=URL.createObjectURL(t),n=document.createElement("a");n.href=o,n.download=s,document.body.appendChild(n),n.click(),n.remove(),setTimeout(()=>URL.revokeObjectURL(o),1e3)}_arm(t){this._armed=this._armed===t?null:t,this._updateZoomButtons(),this._focus&&this._render()}_placeBound(t){if(!this._armed||this._cropDepth>=this._cropMax)return;const e="A"===this._armed?"B":"A";"A"===this._armed?this._zoomA=t:this._zoomB=t;const s=null!=this._zoomA&&null!=this._zoomB;this._armed=s?null:e,this._updateZoomButtons(),s?this._pushCrop(this._zoomA,this._zoomB):this._render()}_updateZoomButtons(){const t=this.options,e=!!this._feature,s=!!t.zoom&&e,o=!!t.exportPng&&e;this._toolbar.style.display=s||o?"":"none",this._btnPng.style.display=o?"":"none";const n=this._cropDepth,i=n<this._cropMax;this._btnA.style.display=s&&i?"":"none",this._btnB.style.display=s&&i?"":"none",this._btnBack.style.display=s&&n>1?"":"none",this._btnAll.style.display=s&&n>0?"":"none",this._btnA.classList.toggle("armed","A"===this._armed),this._btnB.classList.toggle("armed","B"===this._armed)}_applyCrops(){if(!this._crops.length)return this._off=0,this._samples=this._fullSamples,this._stats=this._fullStats,null;const{a:t,b:e}=this._crops[this._crops.length-1],s=this._fullSamples.filter(s=>s.x>=t&&s.x<=e);if(s.length<2)return this._crops.pop(),this._applyCrops();const o=s[0].x,n=null!=s[0].t?s[0].t:0;return this._off=o,this._samples=s.map(t=>({x:t.x-o,z:t.z,coord:t.coord,slope:t.slope,t:null!=t.t?t.t-n:null})),this._stats=this._statsOf(this._samples,!1),s.map(t=>t.coord)}_fitMap(t){const e=this.getMap();if(!e)return null;let s=null;if(t&&t.length?s=h(t):this._feature&&(s=this._feature.getGeometry().getExtent()),!s)return null;const o=e.getView();let n=null;try{n=o.getResolutionForExtent(s,e.getSize())}catch(t){n=null}return o.fit(s,{padding:[40,40,40,40],duration:400}),n}_pushCrop(t,e){if(this._zoomA=null,this._zoomB=null,this._armed=null,this._cropDepth>=this._cropMax)return this._updateZoomButtons(),void this._render();const s=this._off+Math.min(t,e),o=this._off+Math.max(t,e);let n=0;for(let t=0;t<this._fullSamples.length;t++){const e=this._fullSamples[t].x;e>=s&&e<=o&&n++}if(n<2)return this._updateZoomButtons(),void this._render();this._crops.push({a:s,b:o,fitRes:null});const i=this._applyCrops();this._updateZoomButtons(),this._render();const l=this._crops[this._crops.length-1];l&&(l.fitRes=this._fitMap(i))}_applyZoom(){null!=this._zoomA&&null!=this._zoomB&&this._pushCrop(this._zoomA,this._zoomB)}_popCrop(){if(!this._crops.length)return;this._crops.pop(),this._zoomA=null,this._zoomB=null,this._armed=null;const t=this._applyCrops();this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(t)}_exitZoom(){this._crops.length=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._applyCrops(),this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(null)}_closestOnProfile(t){const e=this._feature&&this._feature.getGeometry();if(!e)return null;if(!/Polygon/.test(e.getType()))return e.getClosestPoint(t);const s=this._projectOn(this._fullSamples,t);return s?s.coord:null}_projectOn(t,e){if(!t||!t.length)return null;if(1===t.length)return{x:t[0].x,coord:t[0].coord.slice(0,2)};let s=null,o=1/0;for(let n=1;n<t.length;n++){const i=t[n-1].coord,l=t[n].coord,r=l[0]-i[0],a=l[1]-i[1],h=r*r+a*a;let c=h>0?((e[0]-i[0])*r+(e[1]-i[1])*a)/h:0;c=c<0?0:c>1?1:c;const p=i[0]+r*c,u=i[1]+a*c,d=p-e[0],m=u-e[1],_=d*d+m*m;_<o&&(o=_,s={x:t[n-1].x+(t[n].x-t[n-1].x)*c,coord:[p,u]})}return s}_tooltipText(t){const e=this.options,s=[];return e.tooltipItems.forEach(o=>{var n;"distance"===o?s.push(S(t.x,e.units)):"elevation"===o?s.push(M(t.z,e.units)):"slope"===o?s.push(`${(n=t.slope||0)>=0?"+":""}${n.toFixed(1)} %`):"time"===o&&null!=t.t&&s.push(this._fmtDuration(t.t))}),s.join(" · ")}_setFocus(t){if(!this._focus)return;const e=this._x,s=this._y;this._focus.style("display",null),this._focus.select(".oep-focus-line").attr("x1",e(t.x)).attr("x2",e(t.x)),this._focus.select(".oep-focus-dot").attr("cx",e(t.x)).attr("cy",s(t.z));let o=s(t.z)-16;o<12&&(o=s(t.z)+22);const n=this._focus.select(".oep-focus-txt").attr("x",e(t.x)).attr("y",o).text(this._tooltipText(t)),i=n.node().getBBox();this._focus.select(".oep-focus-bg").attr("x",i.x-4).attr("y",i.y-2).attr("width",i.width+8).attr("height",i.height+4),e(t.x)+i.width/2>this._dims.innerW?n.attr("text-anchor","end"):e(t.x)-i.width/2<0?n.attr("text-anchor","start"):n.attr("text-anchor","middle")}_sampleAt(t){const e=this._samples;if(!e||!e.length)return null;if(1===e.length)return e[0];const s=e[0].x,o=e[e.length-1].x,n=Math.max(s,Math.min(o,t)),i=Math.min(Math.max(w(e,n,1),1),e.length-1),l=e[i-1],r=e[i],a=r.x-l.x,h=a>0?(n-l.x)/a:0,c=(t,e)=>t+(e-t)*h;return{x:n,z:c(l.z,r.z),coord:[c(l.coord[0],r.coord[0]),c(l.coord[1],r.coord[1])],slope:r.slope,t:null!=l.t&&null!=r.t?c(l.t,r.t):null}}_focusByCoord(t){const e=this._projectOn(this._samples,t);if(!e)return;const s=this._sampleAt(e.x);s&&(this._setFocus(s),this._marker&&this._marker.setPosition(s.coord))}_clearFocus(){this._focus&&this._focus.style("display","none"),this._marker&&this._marker.setPosition(void 0)}_clear(){this._body.innerHTML="",this._legendEl.innerHTML="",this._legendEl.style.display="none",this._titleEl.textContent=this.options.labels.empty,this._titleEl.removeAttribute("title"),this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._crops=[],this._off=0,this._demLoading=!1,this._updateZoomButtons(),this._clearFocus(),this.element.style.display="none",this._adjustAttribution()}}R.addTheme=(t,e)=>{p[t]=e},R.THEMES=p,R.DEM_PRESETS=z,R.DemSampler=F,R.POSITIONS=u,R.version="2.1.0";export{R as default};
|
|
18
|
+
*/const p={steelblue:{area:"#4682b4",line:"#3a6d96",axis:"#555",text:"#222",focus:"#e6550d"},lime:{area:"#9ccc2f",line:"#7da521",axis:"#555",text:"#222",focus:"#d62728"},purple:{area:"#9467bd",line:"#76529c",axis:"#555",text:"#222",focus:"#ff9f1c"},slate:{area:"#7c8a99",line:"#4a5560",axis:"#5a6570",text:"#26303a",focus:"#2f81f7"},graphite:{area:"#9a948c",line:"#5c574f",axis:"#5c574f",text:"#2b2823",focus:"#e07a3f"},amber:{area:"#f0a23b",line:"#c4671a",axis:"#7a5a36",text:"#3a2a16",focus:"#1f6fb2"}},u=["top","bottom","left","right","top-left","top-right","bottom-left","bottom-right"],d={en:{distance:"Distance",elevation:"Elevation",slope:"Slope",ascent:"D+",descent:"D-",empty:"Click a track",noElevation:"No elevation data",untitled:"Profile",time:"Time",duration:"Duration",durationUnits:{s:"sec",m:"min",h:"h",d:"d"},zoomStart:"Set start (A)",zoomEnd:"Set end (B)",zoomAll:"Show all",zoomBack:"Back one level",exportPng:"Export as PNG",collapse:"Collapse the profile",expand:"Expand the profile",loading:"Loading the elevation profile"},fr:{distance:"Distance",elevation:"Altitude",slope:"Pente",ascent:"D+",descent:"D-",empty:"Cliquez un tracé",noElevation:"Aucune altimétrie",untitled:"Profil",time:"Temps",duration:"Durée",durationUnits:{s:"sec",m:"min",h:"h",d:"j"},zoomStart:"Définir le début (A)",zoomEnd:"Définir la fin (B)",zoomAll:"Tout voir",zoomBack:"Revenir au niveau précédent",exportPng:"Exporter en PNG",collapse:"Réduire le profil",expand:"Agrandir le profil",loading:"Chargement du profil altimétrique"},es:{distance:"Distancia",elevation:"Altitud",slope:"Pendiente",ascent:"D+",descent:"D-",empty:"Haga clic en una traza",noElevation:"Sin datos de altitud",untitled:"Perfil",time:"Tiempo",duration:"Duración",durationUnits:{s:"seg",m:"min",h:"h",d:"d"},zoomStart:"Definir el inicio (A)",zoomEnd:"Definir el final (B)",zoomAll:"Ver todo",zoomBack:"Volver al nivel anterior",exportPng:"Exportar como PNG",collapse:"Contraer el perfil",expand:"Desplegar el perfil",loading:"Cargando el perfil de elevación"}},m={immersion:"docked",position:"bottom",width:520,height:180,margins:{unit:"px",top:20,right:24,bottom:30,left:48},units:"meters",dataProjection:null,dem:"terrarium",maxPoints:2e3,smoothing:0,theme:"steelblue",color:null,trackLayer:null,transparency:!1,transparencyLevel:.45,grid:!0,slope:!1,slopeClassSize:2.5,slopeColors:null,slopeSeparators:!0,slopeLegend:!0,maxClasses:8,xTicks:null,yTicks:null,verticalScale:"auto",show:"click",showWithoutElevation:!0,collapsable:!0,collapsed:!1,followMap:!0,marker:!0,hideOnMapClick:!0,responsive:!0,mobileBreakpoint:640,zoom:!1,zoomLevels:3,exportPng:!1,ignoreStops:!0,stopSpeed:.5,tooltipItems:["distance","elevation"],headerItems:["distance","ascent","descent","minmax"],titleProperty:"name",titleLink:null,lang:"en",labels:{}};function f(t,e){return _(d[t]||d.en,e||null)}function _(t,e){const s={};return Object.keys(t).forEach(e=>{s[e]=t[e]}),e&&Object.keys(e).forEach(o=>{e[o]&&"object"==typeof e[o]&&!Array.isArray(e[o])&&t[o]&&"object"==typeof t[o]?s[o]=_(t[o],e[o]):s[o]=e[o]}),s}const g=t=>String(t).replace(/[&<>"']/g,t=>({"&":"&","<":"<",">":">",'"':""","'":"'"}[t])),y=t=>"string"==typeof t&&/^(https?:)?\/\/|^mailto:/i.test(t);function x(t){if(!t||!t.getCoordinates)return[];const e=t.getCoordinates();switch(t.getType()){case"LineString":case"LinearRing":return[e];case"MultiLineString":return e;case"Polygon":return e.length?[e[0]]:[];case"MultiPolygon":return e.map(t=>t[0]).filter(Boolean);default:return[]}}function b(t,e){const s=t&&t.getProperties?t.getProperties():{};let o=s.coordTimes;null==o&&s.coordinateProperties&&(o=s.coordinateProperties.times||s.coordinateProperties.coordTimes);let n=null;if(Array.isArray(o)&&(n=Array.isArray(o[0])?o.reduce((t,e)=>t.concat(e),[]):o.slice()),!n&&e){const t=[];let s=!1;for(const o of e)for(const e of o){const o=e.length>3?e[3]:null;t.push(o),null!=o&&isFinite(o)&&(s=!0)}n=s?t:null}if(!n)return null;let i=0;const l=n.map(t=>{if(null==t||""===t)return null;const e="number"==typeof t?t>1e12?t:1e3*t:Date.parse(t);return isFinite(e)?(i++,e):null});return i>=2?l:null}function v(t,e,s){let o=t;if("function"==typeof o)try{o=o(e,s)}catch(t){return null}if(Array.isArray(o)&&(o=o[0]),o&&o.getStroke){const t=o.getStroke();if(t)return t.getColor()}return null}const S=(t,e)=>{if("imperial"===e){const e=t/1609.344;return e<.2?`${Math.round(3.28084*t)} ft`:`${e.toFixed(e<10?2:1)} mi`}return t<1e3?`${Math.round(t)} m`:`${(t/1e3).toFixed(t<1e4?2:1)} km`},E=(t,e)=>"imperial"===e?`${Math.round(3.28084*t)} ft`:`${Math.round(t)} m`;const M='<svg viewBox="0 0 24 24"><path d="M5 13h14" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round"/></svg>',k='<svg viewBox="0 0 24 24"><path d="M3 19l5-7 4 4 4-6 5 9z" fill="currentColor" opacity=".85"/></svg>',w=c.bisector(t=>t.x).left,z={terrarium:{url:"https://s3.amazonaws.com/elevation-tiles-prod/terrarium/{z}/{x}/{y}.png",encoding:"terrarium",maxZoom:14,attributions:'Elevation: <a href="https://registry.opendata.aws/terrain-tiles/">Terrain Tiles</a> (AWS Open Data)'},ign:{api:"ign",url:"https://data.geopf.fr/altimetrie/1.0/calcul/alti/rest/elevation.json",resource:"ign_rge_alti_wld",batch:200,minInterval:1100,attributions:'Elevation: <a href="https://geoservices.ign.fr/rgealti">RGE ALTI</a> (IGN)'}};function C(t){const e=Math.max(1,t.batch||200),s=t.minInterval||0;return o=>{const n=[];let i=0;const l=r=>{if(r>=o.length)return Promise.resolve(n);const a=o.slice(r,r+e),h=Math.max(0,s-(Date.now()-i));return new Promise(t=>setTimeout(t,h)).then(()=>(i=Date.now(),fetch(function(t,e){const s=t=>t.toFixed(6),o=t.url.indexOf("?")>=0?"&":"?";let n=t.url+o+"resource="+encodeURIComponent(t.resource)+"&delimiter=|&zonly=true&lon="+e.map(t=>s(t[0])).join("|")+"&lat="+e.map(t=>s(t[1])).join("|");return t.apiKey&&(n+="&"+(t.apiKeyParam||"apikey")+"="+encodeURIComponent(t.apiKey)),n}(t,a)))).then(t=>t&&t.ok?t.json():null).then(t=>{const s=t&&t.elevations;if(!Array.isArray(s)||s.length!==a.length)return null;for(const t of s)n.push(null==t||t<=-99999?null:t);return l(r+e)})};return l(0)}}const P={source:"terrarium",zoom:"auto",maxZoom:14,maxTiles:32,concurrency:6,tileSize:256},T={terrarium:(t,e,s)=>256*t+e+s/256-32768,mapbox:(t,e,s)=>.1*(65536*t+256*e+s)-1e4},A=20037508.342789244;function $(t,e){const s=t.indexOf("?")>=0?"&":"?";return t.replace(/[?&]$/,"")+s+Object.keys(e).map(t=>t+"="+encodeURIComponent(e[t])).join("&")}function L(t,e,s,o,n){const i=Object.assign({SERVICE:"WMS",REQUEST:"GetMap",VERSION:"1.3.0",FORMAT:"image/png",TRANSPARENT:"false",STYLES:""},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.WIDTH=n,i.HEIGHT=n,i.BBOX=function(t,e,s){const o=2*A/Math.pow(2,t),n=e*o-A,i=A-s*o;return[n,i-o,n+o,i]}(e,s,o).join(","),$(t.url,i)}function j(t){const e=t.olSource,s=t.band||0;return o=>{const l=e.getTileGrid&&e.getTileGrid();return(l?Promise.resolve(null):Promise.resolve(e.getView?e.getView():null)).then(a=>{const h=l||e.getTileGrid&&e.getTileGrid()||a&&a.tileGrid;if(!h)return null;const c=i(a&&a.projection||e.getProjection&&e.getProjection()||"EPSG:3857"),p=h.getResolutions?h.getResolutions().length-1:0,u=e.bandCount||1,d=o.map(t=>n([t[0],t[1]],"EPSG:4326",c)),m=h.getExtent&&h.getExtent()||a&&a.extent||null,f=t=>{const e=h.getResolution(t),s=h.getOrigin(t);let o=h.getTileSize(t);o=Array.isArray(o)?o:[o,o];const n=m?Math.round((m[2]-m[0])/e):1/0,i=m?Math.round((m[3]-m[1])/e):1/0,l=t=>Math.min(n-1,Math.max(0,t)),r=t=>Math.min(i-1,Math.max(0,t)),a=new Map,c=d.map(t=>{const n=(t[0]-s[0])/e-.5,i=(s[1]-t[1])/e-.5,h=l(Math.floor(n)),c=r(Math.floor(i));for(let t=0;t<2;t++)for(let e=0;e<2;e++){const s=Math.floor(l(h+t)/o[0]),n=Math.floor(r(c+e)/o[1]);a.set(s+"/"+n,[s,n])}return{i0:h,j0:c,tx:Math.min(1,Math.max(0,n-h)),ty:Math.min(1,Math.max(0,i-c)),clampI:l,clampJ:r}});return{res:e,origin:s,ts:o,need:a,at:c,clampI:l,clampJ:r}};let _=p,g=f(_);for(;_>0&&g.need.size>t.maxTiles;)_--,g=f(_);if(g.need.size>t.maxTiles)return null;const y=Array.from(g.need.keys());return Promise.all(y.map(t=>{const s=g.need.get(t);return(o=e.getTile(_,s[0],s[1],1,c),new Promise(t=>{const e=()=>{const e=o.getState();return e===r.LOADED?(t(o.getData?o.getData():null),!0):(e===r.ERROR||e===r.EMPTY)&&(t(null),!0)};if(e())return;const s=()=>{e()&&o.removeEventListener("change",s)};o.addEventListener("change",s),o.load&&o.load()})).then(e=>[t,e]);var o})).then(t=>{const e=new Map(t),o=(t,o)=>{const n=Math.floor(g.clampI(t)/g.ts[0]),i=Math.floor(g.clampJ(o)/g.ts[1]);t=g.clampI(t),o=g.clampJ(o);const l=e.get(n+"/"+i);if(!l)return null;const r=t-n*g.ts[0],a=l[((o-i*g.ts[1])*g.ts[0]+r)*u+s];return null!=a&&isFinite(a)?a:null};return g.at.map(t=>{const e=o(t.i0,t.j0),s=o(t.i0+1,t.j0),n=o(t.i0,t.j0+1),i=o(t.i0+1,t.j0+1);if(null==e||null==s||null==n||null==i)return null;const l=e+(s-e)*t.tx;return l+(n+(i-n)*t.tx-l)*t.ty})})})}}function B(t){const e=t.featureInfo,s=Math.max(1,t.concurrency||6);return t=>{const o=new Array(t.length);let n=0,i=!1;const r=()=>{if(i||n>=t.length)return Promise.resolve();const s=n++;return fetch(function(t,e){const s=l([e[0],e[1]]),o=t.resolution||1,n=Object.assign({SERVICE:"WMS",REQUEST:"GetFeatureInfo",VERSION:"1.3.0",INFO_FORMAT:"application/json",STYLES:"",FEATURE_COUNT:1},t.params||{}),i=0===String(n.VERSION).indexOf("1.1")?"SRS":"CRS";return delete n.SRS,delete n.CRS,n[i]=t.projection||"EPSG:3857",n.LAYERS=t.layers,n.QUERY_LAYERS=t.queryLayers||t.layers,n.WIDTH=1,n.HEIGHT=1,n.I=0,n.J=0,n.X=0,n.Y=0,n.BBOX=[s[0]-o,s[1]-o,s[0]+o,s[1]+o].join(","),$(t.url,n)}(e,t[s])).then(t=>t&&t.ok?t.json():null).then(t=>(o[s]=function(t,e){const s=t&&t.features&&t.features[0],o=s&&s.properties;if(!o)return null;if(e){const t=Number(o[e]);return isFinite(t)?t:null}for(const t of Object.keys(o)){const e=Number(o[t]);if(null!==o[t]&&""!==o[t]&&isFinite(e))return e}return null}(t,e.property),r())).catch(()=>{i=!0})},a=[];for(let e=0;e<Math.min(s,t.length);e++)a.push(r());return Promise.all(a).then(()=>i?null:o)}}class F{constructor(t){this.cfg=t,this.decode="function"==typeof t.encoding?t.encoding:T[t.encoding]||T.terrarium,this.tileUrl=function(t){const e=t.olSource;if(e&&"function"==typeof e.getTileUrlFunction){const t=e.getTileUrlFunction(),s=i("EPSG:3857");return(e,o,n)=>t([e,o,n],1,s)}return t.wms?(e,s,o)=>L(t.wms,e,s,o,t.tileSize):(e,s,o)=>t.url.replace("{z}",e).replace("{x}",s).replace("{y}",o)}(t),this.tiles=new Map}_neighbours(t,e,s){const o=function(t,e,s,o){const n=o*Math.pow(2,s),i=Math.sin(e*Math.PI/180);return[(t+180)/360*n,(.5-Math.log((1+i)/(1-i))/(4*Math.PI))*n]}(t,e,s,this.cfg.tileSize),n=o[0]-.5,i=o[1]-.5,l=Math.floor(n),r=Math.floor(i);return{i0:l,j0:r,tx:n-l,ty:i-r}}_key(t,e,s){const o=this.cfg.tileSize,n=o*Math.pow(2,s),i=Math.min(n-1,Math.max(0,e)),l=(t%n+n)%n;return{key:s+"/"+Math.floor(l/o)+"/"+Math.floor(i/o),ii:l,jj:i}}_at(t,e,s){const o=this.cfg.tileSize,n=this._key(t,e,s),i=this.tiles.get(n.key);if(!i)return null;const l=4*(n.jj%o*o+n.ii%o),r=this.decode(i[l],i[l+1],i[l+2],i[l+3]);return null!=r&&isFinite(r)?r:null}sample(t,e,s){const o=this._neighbours(t,e,s),n=this._at(o.i0,o.j0,s),i=this._at(o.i0+1,o.j0,s),l=this._at(o.i0,o.j0+1,s),r=this._at(o.i0+1,o.j0+1,s);if(null==n||null==i||null==l||null==r)return null;const a=n+(i-n)*o.tx;return a+(l+(r-l)*o.tx-a)*o.ty}tilesFor(t,e){const s=new Set;for(const o of t){const t=this._neighbours(o[0],o[1],e);for(let o=0;o<2;o++)for(let n=0;n<2;n++)s.add(this._key(t.i0+o,t.j0+n,e).key)}return s}_fetch(t){const e=t.split("/"),s=this.tileUrl(+e[0],+e[1],+e[2]);return new Promise(t=>{const e=new Image;e.crossOrigin="anonymous",e.onload=()=>{try{const s=this.cfg.tileSize,o=document.createElement("canvas");o.width=s,o.height=s;const n=o.getContext("2d",{willReadFrequently:!0});n.drawImage(e,0,0,s,s),t(n.getImageData(0,0,s,s).data)}catch(e){t(null)}},e.onerror=()=>t(null),e.src=s})}load(t){const e=Array.from(t).filter(t=>!this.tiles.has(t));let s=0,o=!0;const n=()=>{if(s>=e.length)return Promise.resolve();const t=e[s++];return this._fetch(t).then(e=>(this.tiles.set(t,e),e||(o=!1),n()))},i=[];for(let t=0;t<Math.min(this.cfg.concurrency,e.length);t++)i.push(n());return Promise.all(i).then(()=>o)}}class R extends t{constructor(t){const e=_(m,t||{});-1===u.indexOf(e.position)&&(e.position="bottom");const s=e.labels;e.labels=f(e.lang,s);const o=function(t){const e=document.createElement("div");return e.className=`ol-elevation-profile ol-unselectable ol-control oep-pos-${t.position} oep-theme-${"string"==typeof t.theme?t.theme:"custom"}`+("floating"===t.immersion?" oep-floating":""),e}(e);super({element:o,target:t&&t.target}),this.options=e,this._userLabels=s,this.slopeColors=e.slopeColors||null,this._feature=null,this._fullSamples=null,this._fullStats=null,this._samples=null,this._stats=null,this._marker=null,this._collapsed=!!e.collapsed,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._demZ=null,this._demFor=null,this._demSeq=0,this._demLoading=!1,this._trackLines=null,this._linesFor=null,this._onResize=()=>{this._feature&&!this._collapsed&&this._render()},this._buildDom(o),o.style.display="none"}get _cropMode(){return this._crops.length>0}get _cropDepth(){return this._crops.length}get _cropMax(){const t=this.options.zoomLevels;return null==t?3:Math.max(1,0|t)}static featureHasZ(t){const e=t&&t.getGeometry&&t.getGeometry();if(!e)return!1;for(const t of x(e))for(const e of t)if(e.length>2&&isFinite(e[2]))return!0;return!1}static featureHasTime(t){const e=t&&t.getGeometry&&t.getGeometry();return!!e&&!!b(t,x(e))}_buildDom(t){const e=this.options;this._applyTheme(),this._applyTransparency();const s=document.createElement("div");s.className="oep-header",this._titleEl=document.createElement("span"),this._titleEl.className="oep-title",this._titleEl.textContent=e.labels.empty,this._statsEl=document.createElement("span"),this._statsEl.className="oep-stats",s.appendChild(this._titleEl),s.appendChild(this._statsEl),this._toolbar=document.createElement("span"),this._toolbar.className="oep-toolbar";const o=(t,e,s,o)=>{const n=document.createElement("button");return n.type="button",n.className=`oep-tbtn ${t}`,n.innerHTML=e,n.title=s,n.setAttribute("aria-label",s),n.addEventListener("click",o),this._toolbar.appendChild(n),n};this._btnA=o("oep-a",'<svg viewBox="0 0 24 24"><path d="M7 5v14M11 12h8m0 0-3-3m3 3-3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomStart,()=>this._arm("A")),this._btnB=o("oep-b",'<svg viewBox="0 0 24 24"><path d="M17 5v14M13 12H5m0 0 3-3m-3 3 3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomEnd,()=>this._arm("B")),this._btnBack=o("oep-back",'<svg viewBox="0 0 24 24"><path d="M10 6 4 12l6 6M4 12h10a6 6 0 0 1 6 6" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomBack,()=>this._popCrop()),this._btnAll=o("oep-all",'<svg viewBox="0 0 24 24"><path d="M4 12h16M4 12l4-4M4 12l4 4M20 12l-4-4M20 12l-4 4" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomAll,()=>this._exitZoom()),this._btnPng=o("oep-png",'<svg viewBox="0 0 24 24"><path d="M12 4v10m0 0 4-4m-4 4-4-4M5 18h14" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.exportPng,()=>this.exportPNG()),s.appendChild(this._toolbar);const n=document.createElement("button");n.className="oep-toggle",n.type="button",n.innerHTML=this._collapsed?k:M,n.addEventListener("click",()=>this.toggleCollapsed()),s.appendChild(n),this._toggleBtn=n,this._applyToggleLabel(),this._legendEl=document.createElement("div"),this._legendEl.className="oep-legend",this._legendEl.style.display="none",this._body=document.createElement("div"),this._body.className="oep-body",t.appendChild(s),t.appendChild(this._legendEl),t.appendChild(this._body),this._applyCollapsable(),this._updateZoomButtons(),this._collapsed&&t.classList.add("oep-collapsed")}_applyLabels(){const t=this.options.labels,e=(t,e)=>{t&&e&&(t.title=e,t.setAttribute("aria-label",e))};e(this._btnA,t.zoomStart),e(this._btnB,t.zoomEnd),e(this._btnBack,t.zoomBack),e(this._btnAll,t.zoomAll),e(this._btnPng,t.exportPng),this._applyToggleLabel(),this._titleEl&&!this._feature&&(this._titleEl.textContent=t.empty)}_applyToggleLabel(){const t=this.options.labels,e=this._collapsed?t.expand:t.collapse;this._toggleBtn&&e&&(this._toggleBtn.title=e,this._toggleBtn.setAttribute("aria-label",e))}_resolveColor(){const t=this.options;return t.color?"auto"===t.color?this._featureColor():t.color:null}_featureColor(){const t=this._feature;if(!t)return null;const e=this.getMap()?this.getMap().getView().getResolution():1;let s=v(t.getStyle&&t.getStyle(),t,e);return!s&&this.options.trackLayer&&(s=v(this.options.trackLayer.getStyle&&this.options.trackLayer.getStyle(),t,e)),function(t){if(null==t)return null;if("string"==typeof t)return t;if(Array.isArray(t)){const e=t.length>3?t[3]:1;return`rgba(${0|t[0]},${0|t[1]},${0|t[2]},${e})`}return null}(s)}_applyTheme(){const t=this.options,e="object"==typeof t.theme?t.theme:p[t.theme]||p.steelblue;this.themeColors=e;const s=this.element,o=this._resolveColor(),n=o||e.area;let i=e.line;if(o)try{i=String(c.color(o).darker(.7))}catch(t){i=o}s.style.setProperty("--oep-area",n),s.style.setProperty("--oep-line",i),s.style.setProperty("--oep-axis",e.axis),s.style.setProperty("--oep-text",e.text),s.style.setProperty("--oep-focus",e.focus)}_applyTransparency(){const t=this.options.transparency;let e;e=!1===t||null==t?1:!0===t?this.options.transparencyLevel:Math.max(0,Math.min(1,+t)),this.element.style.setProperty("--oep-bg",`rgba(255,255,255,${e})`),this.element.classList.toggle("oep-transparent",e<1)}_applyCollapsable(){const t=this.options.collapsable;this._toggleBtn.style.display=t?"":"none",!t&&this._collapsed&&this.toggleCollapsed(!1)}toggleCollapsed(t){this._collapsed="boolean"==typeof t?t:!this._collapsed,this.element.classList.toggle("oep-collapsed",this._collapsed),this._toggleBtn.innerHTML=this._collapsed?k:M,this._applyToggleLabel(),!this._collapsed&&this._feature&&this._render(),this._adjustAttribution()}_availWidth(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement();return e&&e.clientWidth||("undefined"!=typeof window?window.innerWidth:1024)}_isMobile(){return this.options.responsive&&"undefined"!=typeof window&&window.innerWidth<=(this.options.mobileBreakpoint||640)}_applyPlacement(){const t=this._isMobile();let e=this.options.position;return t&&(e=/top/.test(e)?"top":"bottom"),this.element.className=this.element.className.replace(/oep-pos-\S+/,`oep-pos-${e}`),this.element.classList.toggle("oep-mobile",t),t}_adjustAttribution(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement(),s=e&&e.querySelector&&e.querySelector(".ol-attribution");if(!s)return;if(s.style.bottom="",s.style.right="","none"===this.element.style.display||this._collapsed)return;const o=e.getBoundingClientRect(),n=this.element.getBoundingClientRect();if(!n.height)return;const i=o.bottom-n.bottom,l=o.right-n.right;i<n.height&&l<24&&(s.style.right=`${Math.max(0,Math.round(l))}px`,s.style.bottom=`${Math.round(n.height+2*i)}px`)}setMap(t){const o=this.getMap();if(super.setMap(t),this._mapKeys&&(this._mapKeys.forEach(s),this._mapKeys=null),o&&"undefined"!=typeof window&&window.removeEventListener("resize",this._onResize),this._marker&&!t&&this._marker.setPosition(void 0),!t)return;const n=this.options;if(n.dataProjection||(n.dataProjection=t.getView().getProjection()),n.marker&&!this._marker){const s=document.createElement("div");s.className="oep-marker",this._marker=new e({element:s,positioning:"center-center",stopEvent:!1}),t.addOverlay(this._marker)}"undefined"!=typeof window&&window.addEventListener("resize",this._onResize);const i=e=>t.forEachFeatureAtPixel(e,t=>{const e=t.getGeometry();return(s=e)&&/^(Multi)?(LineString|Polygon)$|^LinearRing$/.test(s.getType())?t:void 0;var s});this._mapKeys=[],this._mapKeys.push(t.on("click",t=>{const e=i(t.pixel);"mouseover"!==this.options.show&&e&&e!==this._feature&&this.setFeature(e),this.options.hideOnMapClick&&!e&&this._feature&&this.clear()})),this._mapKeys.push(t.on("pointermove",e=>{if("mouseover"===this.options.show){const t=i(e.pixel);t&&t!==this._feature&&this.setFeature(t)}if(!this.options.followMap||!this._feature||this._collapsed)return;const s=this._closestOnProfile(e.coordinate);if(!s)return;const o=t.getPixelFromCoordinate(s);o&&(Math.hypot(o[0]-e.pixel[0],o[1]-e.pixel[1])<14?this._focusByCoord(s):this._clearFocus())})),this._mapKeys.push(t.on("moveend",()=>{const e=this._crops[this._crops.length-1];e&&e.fitRes&&t.getView().getResolution()>1.25*e.fitRes&&this._popCrop()})),this._mapKeys.push(t.on("change:size",this._onResize))}setFeature(t){return this._feature=t||null,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,t?(this.element.style.display="",this._compute(),this._fillFromDem(t),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render(),this):(this._fullSamples=this._samples=null,this._demZ=this._demFor=null,this._trackLines=this._linesFor=null,this._clear(),this)}clear(){return this.setFeature(null)}getStats(){return this._stats}setTheme(t){return this.options.theme=t,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setColor(t){return this.options.color=t||null,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setOptions(t){return this.options=_(this.options,t||{}),t&&"slopeColors"in t&&(this.slopeColors=t.slopeColors||null),t&&(t.theme||"color"in t)&&this._applyTheme(),t&&("transparency"in t||"transparencyLevel"in t)&&this._applyTransparency(),t&&"collapsable"in t&&this._applyCollapsable(),t&&"labels"in t&&(this._userLabels=_(this._userLabels||{},t.labels)),t&&("lang"in t||"labels"in t)&&(this.options.labels=f(this.options.lang,this._userLabels),this._applyLabels()),t&&("zoom"in t||"exportPng"in t)&&this._updateZoomButtons(),t&&void 0!==t.width&&"number"==typeof t.width&&(this.options.width=t.width),t&&"dem"in t&&(this._demZ=null,this._demFor=null,this._trackLines=null,this._linesFor=null),this._feature&&(this._compute(),this._fillFromDem(this._feature),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render()),this}_fillFromDem(t){const e=function(t){if(!t)return null;if("function"==typeof t)return Object.assign({},P,{sample:t});const e=!0===t||"string"==typeof t?{source:!0===t?"terrarium":t}:Object.assign({},t);if("function"==typeof e.sample)return Object.assign({},P,e);if(e.track){const t=Object.assign({},P,e);return t.track=Object.assign({coords:"coords",parse:null,fetchOptions:null},"string"==typeof e.track?{url:e.track}:e.track),t.track.url?t:null}if(e.featureInfo){const t=Object.assign({},P,e);return t.sample=B(t),t}if(e.olSource&&"function"!=typeof e.olSource.getTileUrlFunction&&"function"==typeof e.olSource.getTile){const t=Object.assign({},P,e);return t.sample=j(t),t}const s=e.url||e.wms||e.olSource,o=z[e.source]||(s?{}:z.terrarium),n=Object.assign({},P,o,e);return"ign"===n.api?(n.sample=C(n),n):n.url||n.wms||n.olSource?n:null}(this.options.dem);if(!e||!t||this._demFor===t||this._linesFor===t)return;if(R.featureHasZ(t))return;if(!e.sample&&("undefined"==typeof Image||"undefined"==typeof document))return;const s=t.getGeometry&&t.getGeometry(),n=s?x(s):[],i=this.options.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=[];for(const t of n)for(const e of t)l.push(o(e,i));if(!l.length&&!e.track)return;const r=++this._demSeq;this._demLoading=!0;try{this._startFill(e,r,t,l,i)}catch(e){this._demDone(r,t,null,l.length,null,0)}}_startFill(t,e,s,o,n){if(t.track)return void this._startTrackFill(t,e,s,o.length,n);if(t.sample)return void Promise.resolve().then(()=>t.sample(o,{feature:s,projection:n})).then(t=>this._demDone(e,s,t,o.length,null,0)).catch(()=>this._demDone(e,s,null,o.length,null,0));const i=new F(t),l=function(t,e,s){if("number"==typeof s.zoom)return s.zoom;for(let o=s.maxZoom;o>0;o--)if(t.tilesFor(e,o).size<=s.maxTiles)return o;return 1}(i,o,t);i.load(i.tilesFor(o,l)).then(t=>{const n=t?o.map(t=>i.sample(t[0],t[1],l)):null;this._demDone(e,s,n,o.length,l,i.tiles.size)}).catch(()=>this._demDone(e,s,null,o.length,l,0))}_startTrackFill(t,e,s,o,n){const i=function(t,e){if("function"==typeof t)return t(e)||null;if("string"!=typeof t||!e)return null;let s=!0;const o=t.replace(/\{(\w+)\}/g,(t,o)=>{const n=e.get(o);return null==n||""===n?(s=!1,""):encodeURIComponent(String(n))});return s?o:null}(t.track.url,s);i?Promise.resolve().then(()=>fetch(i,t.track.fetchOptions||void 0)).then(t=>{if(!t.ok)throw new Error(String(t.status));return t.json()}).then(i=>{const l=t.track.parse?t.track.parse(i,s):Array.isArray(i)?i:i&&i[t.track.coords];this._trackDone(e,s,l,o,n)}).catch(()=>this._demDone(e,s,null,o,null,0)):this._demDone(e,s,null,o,null,0)}_trackDone(t,e,s,o,i){const l=()=>this._demDone(t,e,null,o,null,0);if(!Array.isArray(s)||!s.length)return l();if("number"==typeof s[0])return void this._demDone(t,e,s,o,null,0);if(t!==this._demSeq||this._feature!==e)return;const r=t=>null!=t&&isFinite(t),a=[];for(const t of s){if(!t||t.length<3||!r(t[0])||!r(t[1])||!r(t[2]))return l();const e=n([t[0],t[1]],"EPSG:4326",i);a.push([e[0],e[1],t[2]])}if(a.length<2)return l();this._demLoading=!1,this._trackLines=[a],this._linesFor=e,this._demZ=null,this._demFor=null,this._compute(),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:!0,zoom:null,tiles:0})}_demDone(t,e,s,o,n,i){if(t!==this._demSeq||this._feature!==e)return;const l=Array.isArray(s)&&s.length===o&&s.every(t=>null!=t&&isFinite(t));this._demLoading=!1,l&&(this._demZ=s,this._demFor=e,this._compute()),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:l,zoom:n,tiles:i})}_compute(){const t=this.options,e=this._linesFor===this._feature&&this._trackLines,s=this._feature.getGeometry&&this._feature.getGeometry(),n=e?this._trackLines:s?x(s):[],i=t.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=this._demFor===this._feature?this._demZ:null,r=e?null:b(this._feature,n);this._hasTime=!!r;const h=!1!==t.ignoreStops,c=null!=t.stopSpeed?t.stopSpeed:.5,p=[];let u=0,d=null,m=-1,f=0,_=null;for(const t of n)for(const e of t){m++;const t=o(e,i);let s=0;d&&(s=a(d,t),u+=s);let n=null;if(r&&null!=r[m]){const t=r[m];if(null!=_){const e=(t-_)/1e3;e>0&&(!h||s/e>=c)&&(f+=e)}n=f,_=t}d=t;const g=e.length>2&&isFinite(e[2])?e[2]:l?l[m]:0;p.push({x:u,z:g,coord:e,t:n})}t.smoothing>0&&this._smooth(p,t.smoothing);const g=this._decimate(p,t.maxPoints);this._addSlope(g),this._fullSamples=g,this._fullStats=this._statsOf(g,!0),this._applyCrops()}_pxPerCm(){try{const t=document.createElement("div");t.style.cssText="position:absolute;left:-9999px;top:0;width:1cm;height:1cm",(this.element||document.body).appendChild(t);const e=t.getBoundingClientRect().height;if(t.remove(),e>0)return e}catch(t){}return 96/2.54}_yScale(t,e,s,o){const n=t.min-e,i=t.max+e,l=s/this._pxPerCm(),r=o/this._pxPerCm(),a=e=>r>0&&e>0?t.distance/r/(e/l):null;let h=this._verticalScaleFor(t,o);if(!(h>0)){const e=c.scaleLinear().domain([n,i]).range([s,0]).nice(),o=e.domain(),l=a(o[1]-o[0]),p=this._plafondExageration();if(!(p>0)||null==l||l<=p)return this._vScale=null,this._vExaggeration=l,e;h=t.distance/r/p}const p=Math.max(h*l,i-n);this._vScale=p/l,this._vExaggeration=a(p);const u=Math.min(0,n);let d=(n+i)/2-p/2;return d<u&&(d=u),c.scaleLinear().domain([d,d+p]).range([s,0])}_plafondExageration(){const t=this.options.verticalScale,e=t&&"object"==typeof t?Number(t.maxExaggeration):0;return e>0?e:0}_verticalScaleFor(t,e){const s=this.options.verticalScale;if("number"==typeof s)return s;const o=s&&"object"==typeof s?Number(s.exaggeration):0;if(!(o>0&&t.distance>0&&e>0))return 0;const n=e/this._pxPerCm();return t.distance/n/o}_statsOf(t,e){let s=0,o=0,n=1/0,i=-1/0,l=0;for(let e=0;e<t.length;e++){const r=t[e].z;if(r<n&&(n=r),r>i&&(i=r),e>0){const n=r-t[e-1].z;n>0?s+=n:o-=n}const a=Math.abs(t[e].slope||0);a>l&&(l=a)}const r=t.length?t[t.length-1].x-t[0].x:0,a=t.length?t[0].t:null,h=t.length?t[t.length-1].t:null;return{distance:r,duration:null!=a&&null!=h?h-a:null,ascent:s,descent:o,min:isFinite(n)?n:0,max:isFinite(i)?i:0,maxAbsSlope:l,points:t.length}}_smooth(t,e){if(!(e>0)||t.length<3)return;const s=e/2,o=t.map(t=>t.z);let n=0,i=0,l=0;for(let e=0;e<t.length;e++){const r=t[e].x;for(;n<t.length&&t[n].x<r-s;)l-=o[n],n++;for(;i<t.length&&t[i].x<=r+s;)l+=o[i],i++;t[e].z=i>n?l/(i-n):o[e]}}_decimate(t,e){const s=t=>({x:t.x,z:t.z,coord:t.coord,t:t.t});if(!e||t.length<=e)return t.map(s);const o=t.length/e,n=[];for(let i=0;i<e;i++)n.push(s(t[Math.floor(i*o)]));return n.push(s(t[t.length-1])),n}_addSlope(t){for(let e=1;e<t.length;e++){const s=t[e].x-t[e-1].x;t[e].slope=s>0?(t[e].z-t[e-1].z)/s*100:0}t.length&&(t[0].slope=t.length>1?t[1].slope:0)}_slopeScale(){const t=this.options.slopeClassSize||2.5,e=this.options.maxClasses||8,s=Math.max(1,Math.floor((this._stats.maxAbsSlope||0)/t)),o=Math.min(s,e-1),n=s>o;let i;if(this.slopeColors&&this.slopeColors.length){const t=c.interpolateRgbBasis(this.slopeColors);i=e=>t(o?e/o:0)}else{const t=c.scaleLinear().domain([0,.16,.42,.68,1]).range(["#2166ac","#27a35a","#ffe000","#f4791f","#d7191c"]).interpolate(c.interpolateRgb).clamp(!0);i=e=>String(t(o?e/o:0))}return{classSize:t,maxIdx:o,capped:n,colorByIndex:i}}_classIndex(t,e){return Math.min(e.maxIdx,Math.floor(Math.abs(t)/e.classSize))}_fmtDuration(t){if(null==t||!isFinite(t))return"";const e=this.options.labels&&this.options.labels.durationUnits||d.en.durationUnits;if((t=Math.max(0,Math.round(t)))<60)return t+" "+e.s;if(t<3600)return Math.round(t/60)+" "+e.m;if(t<86400){let s=Math.floor(t/3600),o=Math.round(t%3600/60);return 60===o&&(s++,o=0),o?`${s} ${e.h} ${o} ${e.m}`:`${s} ${e.h}`}let s=Math.floor(t/86400),o=Math.round(t%86400/3600);return 24===o&&(s++,o=0),o?`${s} ${e.d} ${o} ${e.h}`:`${s} ${e.d}`}_hasElevation(){const t=this._feature;return!!t&&(!!R.featureHasZ(t)||(!(this._demFor!==t||!this._demZ)||!(this._linesFor!==t||!this._trackLines)))}_renderNoElevation(){if(!this.options.showWithoutElevation)return void(this.element.style.display="none");this.element.style.display="",this._applyTheme(),this._applyPlacement(),this._renderHeader(!0);const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-noelev",e.style.height=`${t}px`,e.setAttribute("role","status"),e.textContent=this.options.labels.noElevation,this._body.appendChild(e),this._clearFocus()}_pickProperty(t,e,s){if(!e||!t||!t.get)return null;for(const o of Array.isArray(e)?e:[e]){const e=t.get(o);if(null!=e&&""!==e&&(!s||s(e)))return e}return null}_renderTitle(){const t=this.options,e=this._feature;if(!e)return;const s=this._pickProperty(e,t.titleProperty)||t.labels.untitled,o=this._pickProperty(e,t.titleLink,y);y(o)?this._titleEl.innerHTML=`<a href="${g(o)}" target="_blank" rel="noopener">${g(s)}</a>`:this._titleEl.textContent=s,this._titleEl.setAttribute("title",s)}_renderHeader(t){const e=this.options,s=this._stats,o=this._feature;if(this._renderTitle(),this._demLoading)return this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._legendEl.innerHTML="",void(this._legendEl.style.display="none");const n=[],i=[];if(e.headerItems.forEach(l=>{if("string"==typeof l){if(t&&("ascent"===l||"descent"===l||"min"===l||"max"===l||"minmax"===l))return;if("distance"===l){if(!(s&&s.distance>0))return;n.push(`<b>${S(s.distance,e.units)}</b>`),i.push(S(s.distance,e.units))}else if("ascent"===l)n.push(`<span class="oep-up">${e.labels.ascent} ${E(s.ascent,e.units)}</span>`),i.push(`${e.labels.ascent} ${E(s.ascent,e.units)}`);else if("descent"===l)n.push(`<span class="oep-down">${e.labels.descent} ${E(s.descent,e.units)}</span>`),i.push(`${e.labels.descent} ${E(s.descent,e.units)}`);else if("min"===l)n.push(E(s.min,e.units)),i.push(E(s.min,e.units));else if("max"===l)n.push(E(s.max,e.units)),i.push(E(s.max,e.units));else if("minmax"===l){const t=`${E(s.min,e.units)}-${E(s.max,e.units)}`;n.push(t),i.push(t)}else if("duration"===l&&null!=s.duration){const t=this._fmtDuration(s.duration);n.push(`<span class="oep-time">${g(e.labels.duration)} ${t}</span>`),i.push(`${e.labels.duration} ${t}`)}}else if(l&&l.property){const t=o.get&&o.get(l.property);if(null==t||""===t)return;const e=l.label?`${l.label} `:"";l.asLink&&y(t)?(n.push(`${e}<a href="${g(t)}" target="_blank" rel="noopener">${g(l.linkText||l.label||t)}</a>`),i.push(`${l.label||""} ${t}`)):(n.push(g(e+t)),i.push(e+t))}}),this._statsEl.innerHTML=n.join(" · "),this._statsEl.setAttribute("title",i.join(" · ")),this._legendEl.innerHTML="",e.slope&&e.slopeLegend&&!t){const t=this._slopeScale();for(let e=0;e<=t.maxIdx;e++){const s=t.colorByIndex(e),o=t.capped&&e===t.maxIdx?`≥ ${e*t.classSize} %`:`${e*t.classSize}-${(e+1)*t.classSize} %`,n=document.createElement("span");n.className="oep-leg-it",n.innerHTML=`<i class="oep-sw" style="background:${s}"></i>${o}`,this._legendEl.appendChild(n)}this._legendEl.style.display=""}else this._legendEl.style.display="none"}_renderSpinner(){const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-loading",e.style.height=`${t}px`,e.setAttribute("role","status"),e.setAttribute("aria-label",this.options.labels.loading);const s=document.createElement("div");s.className="oep-spinner",e.appendChild(s),this._body.appendChild(e)}_render(){const t=this.options,e=this._stats,s=this._samples;if(!this._demLoading&&!this._hasElevation())return void this._renderNoElevation();if(!s||!s.length)return;this._applyTheme();const o=this._applyPlacement();if(this._renderHeader(),this._demLoading)return void this._renderSpinner();const n=t.margins,i=n.unit||"px",l=t=>"px"===i?t:t*(parseFloat(getComputedStyle(this.element).fontSize)||16),r=this._availWidth(),a="auto"===t.width||"100%"===t.width||"full"===t.width?r:Math.min("number"==typeof t.width?t.width:parseFloat(t.width)||r,r);this.element.style.width=o?"":`${a}px`;const h=this.element.clientWidth||(o?r:a),p=Math.max(220,h-16),u="number"==typeof t.height?t.height:180,d=l(n.top),m=l(n.right),f=l(n.bottom),_=l(n.left),g=Math.max(10,p-_-m),y=Math.max(10,u-d-f),x=null!=t.xTicks?t.xTicks:Math.max(2,Math.round(g/80)),b=null!=t.yTicks?t.yTicks:Math.max(2,Math.round(y/40));this._body.innerHTML="";const v=c.select(this._body).append("svg").attr("class","oep-svg").attr("width",p).attr("height",u).attr("viewBox",`0 0 ${p} ${u}`),S=v.append("g").attr("transform",`translate(${_},${d})`),E=c.scaleLinear().domain([0,e.distance]).range([0,g]),M=.1*(e.max-e.min)||10,k=this._yScale(e,M,y,g);this._x=E,this._y=k,this._dims={innerW:g,innerH:y},t.grid&&S.append("g").attr("class","oep-grid").call(c.axisLeft(k).ticks(b).tickSize(-g).tickFormat(""));const w="imperial"===t.units?1609.344:1e3;const z=c.area().x(t=>E(t.x)).y0(y).y1(t=>k(t.z));if(t.slope){const e=this._slopeScale(),o=[];let n=1;for(;n<s.length;){const t=this._classIndex(s[n].slope,e);let i=n;for(;i+1<s.length&&this._classIndex(s[i+1].slope,e)===t;)i++;S.append("path").datum(s.slice(n-1,i+1)).attr("class","oep-area-slope").attr("fill",e.colorByIndex(t)).attr("d",z),n>1&&o.push(s[n-1]),n=i+1}t.slopeSeparators&&o.forEach(t=>{S.append("line").attr("class","oep-slope-sep").attr("x1",E(t.x)).attr("x2",E(t.x)).attr("y1",k(t.z)).attr("y2",y)})}else S.append("path").datum(s).attr("class","oep-area").attr("d",z);S.append("path").datum(s).attr("class","oep-line").attr("d",c.line().x(t=>E(t.x)).y(t=>k(t.z))),S.append("g").attr("class","oep-axis oep-axis-x").attr("transform",`translate(0,${y})`).call(c.axisBottom(E).ticks(x).tickFormat(t=>(t/w).toFixed(t/w<10?1:0))),S.append("text").attr("class","oep-axis-label").attr("x",g).attr("y",y+f-4).attr("text-anchor","end").text((t=>"imperial"===t?"mi":"km")(t.units)),S.append("g").attr("class","oep-axis oep-axis-y").call(c.axisLeft(k).ticks(b).tickFormat(e=>"imperial"===t.units?Math.round(3.28084*e):e)),t.zoom&&this._cropDepth<this._cropMax&&[["A",this._zoomA],["B",this._zoomB]].forEach(([t,e])=>{if(null==e)return;const s=E(e);S.append("line").attr("class","oep-ab-line").attr("x1",s).attr("x2",s).attr("y1",0).attr("y2",y),S.append("text").attr("class","oep-ab-label").attr("x",s).attr("y",-6).attr("text-anchor","middle").text(t)});const C=S.append("g").attr("class","oep-focus").style("display","none");C.append("line").attr("class","oep-focus-line").attr("y1",0).attr("y2",y),C.append("circle").attr("class","oep-focus-dot").attr("r",4);const P=C.append("g").attr("class","oep-focus-label");P.append("rect").attr("class","oep-focus-bg"),P.append("text").attr("class","oep-focus-txt"),this._focus=C;const T=t=>{const s=c.pointer(t,S.node())[0];return Math.max(0,Math.min(e.distance,E.invert(s)))},A=v.append("rect").attr("class","oep-overlay").attr("x",_).attr("y",d).attr("width",g).attr("height",y);A.on("mousemove",t=>{const e=this._sampleAt(T(t));e&&(this._setFocus(e),this._marker&&this._marker.setPosition(e.coord))}).on("mouseout",()=>this._clearFocus()),A.on("click",t=>this._placeBound(T(t))),this._armed&&A.style("cursor","col-resize"),this._adjustAttribution()}static get _EXPORT_PROPS(){return["fill","fill-opacity","stroke","stroke-width","stroke-dasharray","stroke-linecap","stroke-linejoin","opacity","font-family","font-size","font-weight","text-anchor","shape-rendering"]}_freezeStyles(t,e){const s=R._EXPORT_PROPS,o=getComputedStyle(t);let n="";for(const t of s){const e=o.getPropertyValue(t);e&&(n+=`${t}:${e};`)}e.setAttribute("style",n);const i=t.children,l=e.children;for(let t=0;t<i.length&&t<l.length;t++)this._freezeStyles(i[t],l[t])}_exportSvg(){const t=this._body.querySelector("svg");if(!t)return null;const e=getComputedStyle(this.element),s=e.getPropertyValue("--oep-bg").trim()||"#fff",o=e.getPropertyValue("--oep-text").trim()||"#222",n=e.fontFamily||"system-ui, sans-serif",i=+t.getAttribute("width"),l=+t.getAttribute("height"),r=this._statsEl.textContent?15:0,a="none"!==this._legendEl.style.display?this._legendEl:null,h=28+r+(a?18:0),c=t.cloneNode(!0);c.querySelectorAll(".oep-focus, .oep-overlay").forEach(t=>t.remove()),this._freezeStyles(t,c);const p=t=>g(String(t)),u=[];if(u.push(`<rect width="${i+16}" height="${l+h+8}" fill="${p(s)}"/>`),u.push(`<text x="8" y="21" style="font-family:${p(n)};font-size:13px;font-weight:600;fill:${p(o)}">${p(this._titleEl.textContent)}</text>`),r&&u.push(`<text x="8" y="38" style="font-family:${p(n)};font-size:11px;fill:${p(o)};opacity:.85">${p(this._statsEl.textContent)}</text>`),a){let t=8;const e=28+r+12;for(const s of a.querySelectorAll(".oep-leg-it")){const i=s.querySelector(".oep-sw"),l=i?getComputedStyle(i).backgroundColor:"none",r=s.textContent.trim();u.push(`<rect x="${t}" y="${e-8}" width="10" height="10" fill="${p(l)}"/>`),u.push(`<text x="${t+14}" y="${e}" style="font-family:${p(n)};font-size:10px;fill:${p(o)}">${p(r)}</text>`),t+=14+5.6*r.length+10}}return u.push(`<g transform="translate(8,${h})">${(new XMLSerializer).serializeToString(c)}</g>`),{width:i+16,height:l+h+8,svg:`<svg xmlns="http://www.w3.org/2000/svg" width="${i+16}" height="${l+h+8}" viewBox="0 0 ${i+16} ${l+h+8}">${u.join("")}</svg>`}}exportPNG(t){const e=t||{},s=this._exportSvg();if(!s)return Promise.reject(new Error("ol-elevation-profile: nothing to export"));const o=e.scale||"undefined"!=typeof window&&window.devicePixelRatio||1;return new Promise((t,n)=>{const i=new Image;i.onload=()=>{try{const l=document.createElement("canvas");l.width=Math.round(s.width*o),l.height=Math.round(s.height*o);const r=l.getContext("2d");r.scale(o,o),r.drawImage(i,0,0),l.toBlob(s=>{s?(!1!==e.download&&this._save(s,e.filename),t(s)):n(new Error("ol-elevation-profile: PNG encoding failed"))},"image/png")}catch(t){n(t)}},i.onerror=()=>n(new Error("ol-elevation-profile: SVG could not be rasterised")),i.src="data:image/svg+xml;charset=utf-8,"+encodeURIComponent(s.svg)})}_save(t,e){const s=e||`${(this._titleEl.textContent||"profile").replace(/[\\/:*?"<>|]+/g,"-").trim()}.png`,o=URL.createObjectURL(t),n=document.createElement("a");n.href=o,n.download=s,document.body.appendChild(n),n.click(),n.remove(),setTimeout(()=>URL.revokeObjectURL(o),1e3)}_arm(t){this._armed=this._armed===t?null:t,this._updateZoomButtons(),this._focus&&this._render()}_placeBound(t){if(!this._armed||this._cropDepth>=this._cropMax)return;const e="A"===this._armed?"B":"A";"A"===this._armed?this._zoomA=t:this._zoomB=t;const s=null!=this._zoomA&&null!=this._zoomB;this._armed=s?null:e,this._updateZoomButtons(),s?this._pushCrop(this._zoomA,this._zoomB):this._render()}_updateZoomButtons(){const t=this.options,e=!!this._feature,s=!!t.zoom&&e,o=!!t.exportPng&&e;this._toolbar.style.display=s||o?"":"none",this._btnPng.style.display=o?"":"none";const n=this._cropDepth,i=n<this._cropMax;this._btnA.style.display=s&&i?"":"none",this._btnB.style.display=s&&i?"":"none",this._btnBack.style.display=s&&n>1?"":"none",this._btnAll.style.display=s&&n>0?"":"none",this._btnA.classList.toggle("armed","A"===this._armed),this._btnB.classList.toggle("armed","B"===this._armed)}_applyCrops(){if(!this._crops.length)return this._off=0,this._samples=this._fullSamples,this._stats=this._fullStats,null;const{a:t,b:e}=this._crops[this._crops.length-1],s=this._fullSamples.filter(s=>s.x>=t&&s.x<=e);if(s.length<2)return this._crops.pop(),this._applyCrops();const o=s[0].x,n=null!=s[0].t?s[0].t:0;return this._off=o,this._samples=s.map(t=>({x:t.x-o,z:t.z,coord:t.coord,slope:t.slope,t:null!=t.t?t.t-n:null})),this._stats=this._statsOf(this._samples,!1),s.map(t=>t.coord)}_fitMap(t){const e=this.getMap();if(!e)return null;let s=null;if(t&&t.length?s=h(t):this._feature&&(s=this._feature.getGeometry().getExtent()),!s)return null;const o=e.getView();let n=null;try{n=o.getResolutionForExtent(s,e.getSize())}catch(t){n=null}return o.fit(s,{padding:[40,40,40,40],duration:400}),n}_pushCrop(t,e){if(this._zoomA=null,this._zoomB=null,this._armed=null,this._cropDepth>=this._cropMax)return this._updateZoomButtons(),void this._render();const s=this._off+Math.min(t,e),o=this._off+Math.max(t,e);let n=0;for(let t=0;t<this._fullSamples.length;t++){const e=this._fullSamples[t].x;e>=s&&e<=o&&n++}if(n<2)return this._updateZoomButtons(),void this._render();this._crops.push({a:s,b:o,fitRes:null});const i=this._applyCrops();this._updateZoomButtons(),this._render();const l=this._crops[this._crops.length-1];l&&(l.fitRes=this._fitMap(i))}_applyZoom(){null!=this._zoomA&&null!=this._zoomB&&this._pushCrop(this._zoomA,this._zoomB)}_popCrop(){if(!this._crops.length)return;this._crops.pop(),this._zoomA=null,this._zoomB=null,this._armed=null;const t=this._applyCrops();this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(t)}_exitZoom(){this._crops.length=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._applyCrops(),this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(null)}_closestOnProfile(t){const e=this._feature&&this._feature.getGeometry();if(!e)return null;if(!/Polygon/.test(e.getType()))return e.getClosestPoint(t);const s=this._projectOn(this._fullSamples,t);return s?s.coord:null}_projectOn(t,e){if(!t||!t.length)return null;if(1===t.length)return{x:t[0].x,coord:t[0].coord.slice(0,2)};let s=null,o=1/0;for(let n=1;n<t.length;n++){const i=t[n-1].coord,l=t[n].coord,r=l[0]-i[0],a=l[1]-i[1],h=r*r+a*a;let c=h>0?((e[0]-i[0])*r+(e[1]-i[1])*a)/h:0;c=c<0?0:c>1?1:c;const p=i[0]+r*c,u=i[1]+a*c,d=p-e[0],m=u-e[1],f=d*d+m*m;f<o&&(o=f,s={x:t[n-1].x+(t[n].x-t[n-1].x)*c,coord:[p,u]})}return s}_tooltipText(t){const e=this.options,s=[];return e.tooltipItems.forEach(o=>{var n;"distance"===o?s.push(S(t.x,e.units)):"elevation"===o?s.push(E(t.z,e.units)):"slope"===o?s.push(`${(n=t.slope||0)>=0?"+":""}${n.toFixed(1)} %`):"time"===o&&null!=t.t&&s.push(this._fmtDuration(t.t))}),s.join(" · ")}_setFocus(t){if(!this._focus)return;const e=this._x,s=this._y;this._focus.style("display",null),this._focus.select(".oep-focus-line").attr("x1",e(t.x)).attr("x2",e(t.x)),this._focus.select(".oep-focus-dot").attr("cx",e(t.x)).attr("cy",s(t.z));let o=s(t.z)-16;o<12&&(o=s(t.z)+22);const n=this._focus.select(".oep-focus-txt").attr("x",e(t.x)).attr("y",o).text(this._tooltipText(t)),i=n.node().getBBox();this._focus.select(".oep-focus-bg").attr("x",i.x-4).attr("y",i.y-2).attr("width",i.width+8).attr("height",i.height+4),e(t.x)+i.width/2>this._dims.innerW?n.attr("text-anchor","end"):e(t.x)-i.width/2<0?n.attr("text-anchor","start"):n.attr("text-anchor","middle")}_sampleAt(t){const e=this._samples;if(!e||!e.length)return null;if(1===e.length)return e[0];const s=e[0].x,o=e[e.length-1].x,n=Math.max(s,Math.min(o,t)),i=Math.min(Math.max(w(e,n,1),1),e.length-1),l=e[i-1],r=e[i],a=r.x-l.x,h=a>0?(n-l.x)/a:0,c=(t,e)=>t+(e-t)*h;return{x:n,z:c(l.z,r.z),coord:[c(l.coord[0],r.coord[0]),c(l.coord[1],r.coord[1])],slope:r.slope,t:null!=l.t&&null!=r.t?c(l.t,r.t):null}}_focusByCoord(t){const e=this._projectOn(this._samples,t);if(!e)return;const s=this._sampleAt(e.x);s&&(this._setFocus(s),this._marker&&this._marker.setPosition(s.coord))}_clearFocus(){this._focus&&this._focus.style("display","none"),this._marker&&this._marker.setPosition(void 0)}_clear(){this._body.innerHTML="",this._legendEl.innerHTML="",this._legendEl.style.display="none",this._titleEl.textContent=this.options.labels.empty,this._titleEl.removeAttribute("title"),this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._crops=[],this._off=0,this._demLoading=!1,this._updateZoomButtons(),this._clearFocus(),this.element.style.display="none",this._adjustAttribution()}}R.addTheme=(t,e)=>{p[t]=e},R.THEMES=p,R.DEM_PRESETS=z,R.DemSampler=F,R.POSITIONS=u,R.version="2.1.2";export{R as default};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! ol-elevation-profile 2.1.
|
|
1
|
+
/*! ol-elevation-profile 2.1.2 | MIT License | https://github.com/lc-4918/ol-elevation-profile */
|
|
2
2
|
(function (global, factory) {
|
|
3
3
|
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory(require('ol/control/Control.js'), require('ol/Overlay.js'), require('ol/Observable.js'), require('ol/proj.js'), require('ol/TileState.js'), require('ol/sphere.js'), require('ol/extent.js'), require('d3')) :
|
|
4
4
|
typeof define === 'function' && define.amd ? define(['ol/control/Control.js', 'ol/Overlay.js', 'ol/Observable.js', 'ol/proj.js', 'ol/TileState.js', 'ol/sphere.js', 'ol/extent.js', 'd3'], factory) :
|
|
@@ -132,7 +132,8 @@
|
|
|
132
132
|
yTicks: null,
|
|
133
133
|
verticalScale: 'auto', // 'auto' : le profil remplit la hauteur ;
|
|
134
134
|
// un nombre : mètres par centimètre physique ;
|
|
135
|
-
// { exaggeration } : rapport fixe vertical/horizontal
|
|
135
|
+
// { exaggeration } : rapport fixe vertical/horizontal ;
|
|
136
|
+
// { maxExaggeration } : 'auto' sans dépasser ce rapport
|
|
136
137
|
show: 'click',
|
|
137
138
|
showWithoutElevation: true, // trace sans Z, et aucun MNT n'a pu en fournir :
|
|
138
139
|
// le panneau paraît quand même, avec un message
|
|
@@ -854,16 +855,22 @@
|
|
|
854
855
|
* @property {number} [smoothing=0] Elevation smoothing window, in METERS (0 = none).
|
|
855
856
|
* @property {?number} [xTicks=null] X axis ticks (null = auto from width).
|
|
856
857
|
* @property {?number} [yTicks=null] Y axis ticks (null = auto from height).
|
|
857
|
-
* @property {('auto'|number|{exaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
858
|
+
* @property {('auto'|number|{exaggeration:number}|{maxExaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
858
859
|
* profile fills the height, which is legible but changes scale from one track to the
|
|
859
860
|
* next, so a 2 % ramp looks like a wall and two profiles cannot be compared. A number
|
|
860
861
|
* fixes the metres covered per physical centimetre, which makes RANGES comparable.
|
|
861
862
|
* `{exaggeration}` fixes the ratio between the two axes instead, which makes SLOPES
|
|
862
863
|
* comparable: the gradient read off the chart is the real one, multiplied by the same
|
|
863
864
|
* factor on every track, and the control recomputes it per track and per A/B crop.
|
|
864
|
-
*
|
|
865
|
-
*
|
|
866
|
-
*
|
|
865
|
+
* `{maxExaggeration}` keeps `'auto'` — the height is filled, which reads best — and
|
|
866
|
+
* only reins in the absurd: a short, gently sloping track whose 2 % ramp would
|
|
867
|
+
* otherwise be drawn as a wall. A track already under the cap is untouched, so unlike
|
|
868
|
+
* a fixed exaggeration it never flattens a mountain traverse to fit a rule.
|
|
869
|
+
* A number or `{exaggeration}` is a **floor**, not a cage: a track whose range exceeds
|
|
870
|
+
* what the height can show would spill out of the frame, which is worse than losing
|
|
871
|
+
* comparability, so the scale then widens silently, nothing being drawn on the chart
|
|
872
|
+
* to say so. The extra room the scale asks for is added ABOVE the track, never below:
|
|
873
|
+
* centring it would push the axis under sea level on a mountain profile.
|
|
867
874
|
* @property {'click'|'mouseover'} [show='click'] How a track is selected on the map.
|
|
868
875
|
* @property {boolean} [showWithoutElevation=true] What to do with a track that ends up
|
|
869
876
|
* with no elevation at all: none in its geometry, and none the terrain model could
|
|
@@ -1523,23 +1530,44 @@
|
|
|
1523
1530
|
// La publier partout est le seul moyen de voir la différence plutôt que d'y croire.
|
|
1524
1531
|
const rapport = (etendue) => (cmH > 0 && etendue > 0) ? (s.distance / cmH) / (etendue / cm) : null;
|
|
1525
1532
|
|
|
1526
|
-
|
|
1533
|
+
let vs = this._verticalScaleFor(s, innerW);
|
|
1527
1534
|
if (!(vs > 0)) {
|
|
1528
1535
|
// `'auto'` : la hauteur est remplie, donc c'est l'amplitude qui décide de tout.
|
|
1529
1536
|
// `nice()` arrondit le domaine vers l'extérieur, d'où la lecture APRÈS coup.
|
|
1530
1537
|
const echelle = d3__namespace.scaleLinear().domain([bas, haut]).range([innerH, 0]).nice();
|
|
1531
1538
|
const dom = echelle.domain();
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1539
|
+
const obtenu = rapport(dom[1] - dom[0]);
|
|
1540
|
+
// Un PLAFOND d'exagération, s'il en est demandé un. Remplir la hauteur est ce
|
|
1541
|
+
// qui se lit le mieux, mais sur une trace courte et peu accidentée cela dresse
|
|
1542
|
+
// une pente de 2 % en muraille. Le plafond n'intervient que là : quand le
|
|
1543
|
+
// remplissage dépasse le rapport permis, on élargit l'échelle jusqu'à lui. Une
|
|
1544
|
+
// trace assez accidentée pour rester en dessous n'est jamais aplatie, ce qu'une
|
|
1545
|
+
// exagération FIXE lui imposerait — à 680 km d'une traversée, elle n'occuperait
|
|
1546
|
+
// plus qu'un dixième du cadre.
|
|
1547
|
+
const plafond = this._plafondExageration();
|
|
1548
|
+
if (!(plafond > 0) || obtenu == null || obtenu <= plafond) {
|
|
1549
|
+
this._vScale = null; // aucune échelle absolue demandée
|
|
1550
|
+
this._vExaggeration = obtenu;
|
|
1551
|
+
return echelle;
|
|
1552
|
+
}
|
|
1553
|
+
vs = (s.distance / cmH) / plafond; // l'échelle qui donne exactement le plafond
|
|
1535
1554
|
}
|
|
1536
1555
|
const etendue = Math.max(vs * cm, haut - bas); // jamais moins qu'il n'en faut
|
|
1537
|
-
const milieu = (bas + haut) / 2;
|
|
1538
1556
|
this._vScale = etendue / cm; // m/cm effectivement appliqués
|
|
1539
1557
|
// Sous le plancher, le rapport retombe sous celui demandé : c'est la seule façon de
|
|
1540
1558
|
// savoir que c'est arrivé.
|
|
1541
1559
|
this._vExaggeration = rapport(etendue);
|
|
1542
|
-
|
|
1560
|
+
|
|
1561
|
+
// La marge que l'échelle impose se place AU-DESSUS, pas de part et d'autre.
|
|
1562
|
+
// Centrer la fenêtre creuse sous la trace : une échelle large - ce que demande
|
|
1563
|
+
// une exagération fixe sur une trace longue - fait alors descendre l'axe sous le
|
|
1564
|
+
// niveau de la mer, et on lit « -900 m » sur un profil de montagne. Le plancher
|
|
1565
|
+
// est donc zéro, ou le point le plus bas de la trace s'il passe dessous : une
|
|
1566
|
+
// dépression existe, une altitude négative inventée, non.
|
|
1567
|
+
const plancher = Math.min(0, bas);
|
|
1568
|
+
let y0 = (bas + haut) / 2 - etendue / 2; // le centrage, quand il tient
|
|
1569
|
+
if (y0 < plancher) y0 = plancher;
|
|
1570
|
+
return d3__namespace.scaleLinear().domain([y0, y0 + etendue]).range([innerH, 0]);
|
|
1543
1571
|
}
|
|
1544
1572
|
|
|
1545
1573
|
/**
|
|
@@ -1557,6 +1585,13 @@
|
|
|
1557
1585
|
*
|
|
1558
1586
|
* @private
|
|
1559
1587
|
*/
|
|
1588
|
+
/** Le rapport à ne pas dépasser, `0` s'il n'en est pas demandé. @private */
|
|
1589
|
+
_plafondExageration() {
|
|
1590
|
+
const v = this.options.verticalScale;
|
|
1591
|
+
const n = (v && typeof v === 'object') ? Number(v.maxExaggeration) : 0;
|
|
1592
|
+
return n > 0 ? n : 0;
|
|
1593
|
+
}
|
|
1594
|
+
|
|
1560
1595
|
_verticalScaleFor(s, innerW) {
|
|
1561
1596
|
const v = this.options.verticalScale;
|
|
1562
1597
|
if (typeof v === 'number') return v;
|
|
@@ -1766,7 +1801,9 @@
|
|
|
1766
1801
|
this._statsEl.setAttribute('title', text.join(' · '));
|
|
1767
1802
|
|
|
1768
1803
|
this._legendEl.innerHTML = '';
|
|
1769
|
-
|
|
1804
|
+
// Une légende de pentes sans altitude ne légende rien : elle annoncerait des
|
|
1805
|
+
// classes qu'aucun trait ne porte, sous un panneau qui dit n'avoir pas de profil.
|
|
1806
|
+
if (o.slope && o.slopeLegend && !sansAltimetrie) {
|
|
1770
1807
|
const sc = this._slopeScale();
|
|
1771
1808
|
for (let idx = 0; idx <= sc.maxIdx; idx++) {
|
|
1772
1809
|
const color = sc.colorByIndex(idx);
|
|
@@ -2275,7 +2312,7 @@
|
|
|
2275
2312
|
// Stamped at build time from package.json - see rollup.config.mjs, which fails the build
|
|
2276
2313
|
// if this placeholder ever stops matching. Read from the source rather than the bundle,
|
|
2277
2314
|
// it says just that: a development copy, of no released version.
|
|
2278
|
-
ElevationProfile.version = '2.1.
|
|
2315
|
+
ElevationProfile.version = '2.1.2';
|
|
2279
2316
|
|
|
2280
2317
|
return ElevationProfile;
|
|
2281
2318
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! ol-elevation-profile 2.1.
|
|
1
|
+
/*! ol-elevation-profile 2.1.2 | MIT License | https://github.com/lc-4918/ol-elevation-profile */
|
|
2
2
|
!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e(require("ol/control/Control.js"),require("ol/Overlay.js"),require("ol/Observable.js"),require("ol/proj.js"),require("ol/TileState.js"),require("ol/sphere.js"),require("ol/extent.js"),require("d3")):"function"==typeof define&&define.amd?define(["ol/control/Control.js","ol/Overlay.js","ol/Observable.js","ol/proj.js","ol/TileState.js","ol/sphere.js","ol/extent.js","d3"],e):(t="undefined"!=typeof globalThis?globalThis:t||self).OlElevationProfile=e(t.ol.control.Control,t.ol.Overlay,t.ol.Observable,t.ol.proj,t.ol.TileState,t.ol.sphere,t.ol.extent,t.d3)}(this,function(t,e,s,o,n,i,l,r){"use strict";function a(t){var e=Object.create(null);return t&&Object.keys(t).forEach(function(s){if("default"!==s){var o=Object.getOwnPropertyDescriptor(t,s);Object.defineProperty(e,s,o.get?o:{enumerable:!0,get:function(){return t[s]}})}}),e.default=t,Object.freeze(e)}var h=a(r);
|
|
3
3
|
/**
|
|
4
4
|
* Synchronized elevation profile control for OpenLayers, rendered with d3.
|
|
@@ -15,4 +15,4 @@
|
|
|
15
15
|
*
|
|
16
16
|
* @module ol-elevation-profile
|
|
17
17
|
* @license MIT
|
|
18
|
-
*/const c={steelblue:{area:"#4682b4",line:"#3a6d96",axis:"#555",text:"#222",focus:"#e6550d"},lime:{area:"#9ccc2f",line:"#7da521",axis:"#555",text:"#222",focus:"#d62728"},purple:{area:"#9467bd",line:"#76529c",axis:"#555",text:"#222",focus:"#ff9f1c"},slate:{area:"#7c8a99",line:"#4a5560",axis:"#5a6570",text:"#26303a",focus:"#2f81f7"},graphite:{area:"#9a948c",line:"#5c574f",axis:"#5c574f",text:"#2b2823",focus:"#e07a3f"},amber:{area:"#f0a23b",line:"#c4671a",axis:"#7a5a36",text:"#3a2a16",focus:"#1f6fb2"}},u=["top","bottom","left","right","top-left","top-right","bottom-left","bottom-right"],p={en:{distance:"Distance",elevation:"Elevation",slope:"Slope",ascent:"D+",descent:"D-",empty:"Click a track",noElevation:"No elevation data",untitled:"Profile",time:"Time",duration:"Duration",durationUnits:{s:"sec",m:"min",h:"h",d:"d"},zoomStart:"Set start (A)",zoomEnd:"Set end (B)",zoomAll:"Show all",zoomBack:"Back one level",exportPng:"Export as PNG",collapse:"Collapse the profile",expand:"Expand the profile",loading:"Loading the elevation profile"},fr:{distance:"Distance",elevation:"Altitude",slope:"Pente",ascent:"D+",descent:"D-",empty:"Cliquez un tracé",noElevation:"Aucune altimétrie",untitled:"Profil",time:"Temps",duration:"Durée",durationUnits:{s:"sec",m:"min",h:"h",d:"j"},zoomStart:"Définir le début (A)",zoomEnd:"Définir la fin (B)",zoomAll:"Tout voir",zoomBack:"Revenir au niveau précédent",exportPng:"Exporter en PNG",collapse:"Réduire le profil",expand:"Agrandir le profil",loading:"Chargement du profil altimétrique"},es:{distance:"Distancia",elevation:"Altitud",slope:"Pendiente",ascent:"D+",descent:"D-",empty:"Haga clic en una traza",noElevation:"Sin datos de altitud",untitled:"Perfil",time:"Tiempo",duration:"Duración",durationUnits:{s:"seg",m:"min",h:"h",d:"d"},zoomStart:"Definir el inicio (A)",zoomEnd:"Definir el final (B)",zoomAll:"Ver todo",zoomBack:"Volver al nivel anterior",exportPng:"Exportar como PNG",collapse:"Contraer el perfil",expand:"Desplegar el perfil",loading:"Cargando el perfil de elevación"}},d={immersion:"docked",position:"bottom",width:520,height:180,margins:{unit:"px",top:20,right:24,bottom:30,left:48},units:"meters",dataProjection:null,dem:"terrarium",maxPoints:2e3,smoothing:0,theme:"steelblue",color:null,trackLayer:null,transparency:!1,transparencyLevel:.45,grid:!0,slope:!1,slopeClassSize:2.5,slopeColors:null,slopeSeparators:!0,slopeLegend:!0,maxClasses:8,xTicks:null,yTicks:null,verticalScale:"auto",show:"click",showWithoutElevation:!0,collapsable:!0,collapsed:!1,followMap:!0,marker:!0,hideOnMapClick:!0,responsive:!0,mobileBreakpoint:640,zoom:!1,zoomLevels:3,exportPng:!1,ignoreStops:!0,stopSpeed:.5,tooltipItems:["distance","elevation"],headerItems:["distance","ascent","descent","minmax"],titleProperty:"name",titleLink:null,lang:"en",labels:{}};function m(t,e){return f(p[t]||p.en,e||null)}function f(t,e){const s={};return Object.keys(t).forEach(e=>{s[e]=t[e]}),e&&Object.keys(e).forEach(o=>{e[o]&&"object"==typeof e[o]&&!Array.isArray(e[o])&&t[o]&&"object"==typeof t[o]?s[o]=f(t[o],e[o]):s[o]=e[o]}),s}const _=t=>String(t).replace(/[&<>"']/g,t=>({"&":"&","<":"<",">":">",'"':""","'":"'"}[t])),g=t=>"string"==typeof t&&/^(https?:)?\/\/|^mailto:/i.test(t);function y(t){if(!t||!t.getCoordinates)return[];const e=t.getCoordinates();switch(t.getType()){case"LineString":case"LinearRing":return[e];case"MultiLineString":return e;case"Polygon":return e.length?[e[0]]:[];case"MultiPolygon":return e.map(t=>t[0]).filter(Boolean);default:return[]}}function x(t,e){const s=t&&t.getProperties?t.getProperties():{};let o=s.coordTimes;null==o&&s.coordinateProperties&&(o=s.coordinateProperties.times||s.coordinateProperties.coordTimes);let n=null;if(Array.isArray(o)&&(n=Array.isArray(o[0])?o.reduce((t,e)=>t.concat(e),[]):o.slice()),!n&&e){const t=[];let s=!1;for(const o of e)for(const e of o){const o=e.length>3?e[3]:null;t.push(o),null!=o&&isFinite(o)&&(s=!0)}n=s?t:null}if(!n)return null;let i=0;const l=n.map(t=>{if(null==t||""===t)return null;const e="number"==typeof t?t>1e12?t:1e3*t:Date.parse(t);return isFinite(e)?(i++,e):null});return i>=2?l:null}function b(t,e,s){let o=t;if("function"==typeof o)try{o=o(e,s)}catch(t){return null}if(Array.isArray(o)&&(o=o[0]),o&&o.getStroke){const t=o.getStroke();if(t)return t.getColor()}return null}const v=(t,e)=>{if("imperial"===e){const e=t/1609.344;return e<.2?`${Math.round(3.28084*t)} ft`:`${e.toFixed(e<10?2:1)} mi`}return t<1e3?`${Math.round(t)} m`:`${(t/1e3).toFixed(t<1e4?2:1)} km`},S=(t,e)=>"imperial"===e?`${Math.round(3.28084*t)} ft`:`${Math.round(t)} m`;const E='<svg viewBox="0 0 24 24"><path d="M5 13h14" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round"/></svg>',M='<svg viewBox="0 0 24 24"><path d="M3 19l5-7 4 4 4-6 5 9z" fill="currentColor" opacity=".85"/></svg>',k=h.bisector(t=>t.x).left,w={terrarium:{url:"https://s3.amazonaws.com/elevation-tiles-prod/terrarium/{z}/{x}/{y}.png",encoding:"terrarium",maxZoom:14,attributions:'Elevation: <a href="https://registry.opendata.aws/terrain-tiles/">Terrain Tiles</a> (AWS Open Data)'},ign:{api:"ign",url:"https://data.geopf.fr/altimetrie/1.0/calcul/alti/rest/elevation.json",resource:"ign_rge_alti_wld",batch:200,minInterval:1100,attributions:'Elevation: <a href="https://geoservices.ign.fr/rgealti">RGE ALTI</a> (IGN)'}};function z(t){const e=Math.max(1,t.batch||200),s=t.minInterval||0;return o=>{const n=[];let i=0;const l=r=>{if(r>=o.length)return Promise.resolve(n);const a=o.slice(r,r+e),h=Math.max(0,s-(Date.now()-i));return new Promise(t=>setTimeout(t,h)).then(()=>(i=Date.now(),fetch(function(t,e){const s=t=>t.toFixed(6),o=t.url.indexOf("?")>=0?"&":"?";let n=t.url+o+"resource="+encodeURIComponent(t.resource)+"&delimiter=|&zonly=true&lon="+e.map(t=>s(t[0])).join("|")+"&lat="+e.map(t=>s(t[1])).join("|");return t.apiKey&&(n+="&"+(t.apiKeyParam||"apikey")+"="+encodeURIComponent(t.apiKey)),n}(t,a)))).then(t=>t&&t.ok?t.json():null).then(t=>{const s=t&&t.elevations;if(!Array.isArray(s)||s.length!==a.length)return null;for(const t of s)n.push(null==t||t<=-99999?null:t);return l(r+e)})};return l(0)}}const C={source:"terrarium",zoom:"auto",maxZoom:14,maxTiles:32,concurrency:6,tileSize:256},P={terrarium:(t,e,s)=>256*t+e+s/256-32768,mapbox:(t,e,s)=>.1*(65536*t+256*e+s)-1e4},T=20037508.342789244;function j(t,e){const s=t.indexOf("?")>=0?"&":"?";return t.replace(/[?&]$/,"")+s+Object.keys(e).map(t=>t+"="+encodeURIComponent(e[t])).join("&")}function A(t,e,s,o,n){const i=Object.assign({SERVICE:"WMS",REQUEST:"GetMap",VERSION:"1.3.0",FORMAT:"image/png",TRANSPARENT:"false",STYLES:""},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.WIDTH=n,i.HEIGHT=n,i.BBOX=function(t,e,s){const o=2*T/Math.pow(2,t),n=e*o-T,i=T-s*o;return[n,i-o,n+o,i]}(e,s,o).join(","),j(t.url,i)}function L(t){const e=t.olSource,s=t.band||0;return i=>{const l=e.getTileGrid&&e.getTileGrid();return(l?Promise.resolve(null):Promise.resolve(e.getView?e.getView():null)).then(r=>{const a=l||e.getTileGrid&&e.getTileGrid()||r&&r.tileGrid;if(!a)return null;const h=o.get(r&&r.projection||e.getProjection&&e.getProjection()||"EPSG:3857"),c=a.getResolutions?a.getResolutions().length-1:0,u=e.bandCount||1,p=i.map(t=>o.transform([t[0],t[1]],"EPSG:4326",h)),d=a.getExtent&&a.getExtent()||r&&r.extent||null,m=t=>{const e=a.getResolution(t),s=a.getOrigin(t);let o=a.getTileSize(t);o=Array.isArray(o)?o:[o,o];const n=d?Math.round((d[2]-d[0])/e):1/0,i=d?Math.round((d[3]-d[1])/e):1/0,l=t=>Math.min(n-1,Math.max(0,t)),r=t=>Math.min(i-1,Math.max(0,t)),h=new Map,c=p.map(t=>{const n=(t[0]-s[0])/e-.5,i=(s[1]-t[1])/e-.5,a=l(Math.floor(n)),c=r(Math.floor(i));for(let t=0;t<2;t++)for(let e=0;e<2;e++){const s=Math.floor(l(a+t)/o[0]),n=Math.floor(r(c+e)/o[1]);h.set(s+"/"+n,[s,n])}return{i0:a,j0:c,tx:Math.min(1,Math.max(0,n-a)),ty:Math.min(1,Math.max(0,i-c)),clampI:l,clampJ:r}});return{res:e,origin:s,ts:o,need:h,at:c,clampI:l,clampJ:r}};let f=c,_=m(f);for(;f>0&&_.need.size>t.maxTiles;)f--,_=m(f);if(_.need.size>t.maxTiles)return null;const g=Array.from(_.need.keys());return Promise.all(g.map(t=>{const s=_.need.get(t);return(o=e.getTile(f,s[0],s[1],1,h),new Promise(t=>{const e=()=>{const e=o.getState();return e===n.LOADED?(t(o.getData?o.getData():null),!0):(e===n.ERROR||e===n.EMPTY)&&(t(null),!0)};if(e())return;const s=()=>{e()&&o.removeEventListener("change",s)};o.addEventListener("change",s),o.load&&o.load()})).then(e=>[t,e]);var o})).then(t=>{const e=new Map(t),o=(t,o)=>{const n=Math.floor(_.clampI(t)/_.ts[0]),i=Math.floor(_.clampJ(o)/_.ts[1]);t=_.clampI(t),o=_.clampJ(o);const l=e.get(n+"/"+i);if(!l)return null;const r=t-n*_.ts[0],a=l[((o-i*_.ts[1])*_.ts[0]+r)*u+s];return null!=a&&isFinite(a)?a:null};return _.at.map(t=>{const e=o(t.i0,t.j0),s=o(t.i0+1,t.j0),n=o(t.i0,t.j0+1),i=o(t.i0+1,t.j0+1);if(null==e||null==s||null==n||null==i)return null;const l=e+(s-e)*t.tx;return l+(n+(i-n)*t.tx-l)*t.ty})})})}}function $(t){const e=t.featureInfo,s=Math.max(1,t.concurrency||6);return t=>{const n=new Array(t.length);let i=0,l=!1;const r=()=>{if(l||i>=t.length)return Promise.resolve();const s=i++;return fetch(function(t,e){const s=o.fromLonLat([e[0],e[1]]),n=t.resolution||1,i=Object.assign({SERVICE:"WMS",REQUEST:"GetFeatureInfo",VERSION:"1.3.0",INFO_FORMAT:"application/json",STYLES:"",FEATURE_COUNT:1},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.QUERY_LAYERS=t.queryLayers||t.layers,i.WIDTH=1,i.HEIGHT=1,i.I=0,i.J=0,i.X=0,i.Y=0,i.BBOX=[s[0]-n,s[1]-n,s[0]+n,s[1]+n].join(","),j(t.url,i)}(e,t[s])).then(t=>t&&t.ok?t.json():null).then(t=>(n[s]=function(t,e){const s=t&&t.features&&t.features[0],o=s&&s.properties;if(!o)return null;if(e){const t=Number(o[e]);return isFinite(t)?t:null}for(const t of Object.keys(o)){const e=Number(o[t]);if(null!==o[t]&&""!==o[t]&&isFinite(e))return e}return null}(t,e.property),r())).catch(()=>{l=!0})},a=[];for(let e=0;e<Math.min(s,t.length);e++)a.push(r());return Promise.all(a).then(()=>l?null:n)}}class B{constructor(t){this.cfg=t,this.decode="function"==typeof t.encoding?t.encoding:P[t.encoding]||P.terrarium,this.tileUrl=function(t){const e=t.olSource;if(e&&"function"==typeof e.getTileUrlFunction){const t=e.getTileUrlFunction(),s=o.get("EPSG:3857");return(e,o,n)=>t([e,o,n],1,s)}return t.wms?(e,s,o)=>A(t.wms,e,s,o,t.tileSize):(e,s,o)=>t.url.replace("{z}",e).replace("{x}",s).replace("{y}",o)}(t),this.tiles=new Map}_neighbours(t,e,s){const o=function(t,e,s,o){const n=o*Math.pow(2,s),i=Math.sin(e*Math.PI/180);return[(t+180)/360*n,(.5-Math.log((1+i)/(1-i))/(4*Math.PI))*n]}(t,e,s,this.cfg.tileSize),n=o[0]-.5,i=o[1]-.5,l=Math.floor(n),r=Math.floor(i);return{i0:l,j0:r,tx:n-l,ty:i-r}}_key(t,e,s){const o=this.cfg.tileSize,n=o*Math.pow(2,s),i=Math.min(n-1,Math.max(0,e)),l=(t%n+n)%n;return{key:s+"/"+Math.floor(l/o)+"/"+Math.floor(i/o),ii:l,jj:i}}_at(t,e,s){const o=this.cfg.tileSize,n=this._key(t,e,s),i=this.tiles.get(n.key);if(!i)return null;const l=4*(n.jj%o*o+n.ii%o),r=this.decode(i[l],i[l+1],i[l+2],i[l+3]);return null!=r&&isFinite(r)?r:null}sample(t,e,s){const o=this._neighbours(t,e,s),n=this._at(o.i0,o.j0,s),i=this._at(o.i0+1,o.j0,s),l=this._at(o.i0,o.j0+1,s),r=this._at(o.i0+1,o.j0+1,s);if(null==n||null==i||null==l||null==r)return null;const a=n+(i-n)*o.tx;return a+(l+(r-l)*o.tx-a)*o.ty}tilesFor(t,e){const s=new Set;for(const o of t){const t=this._neighbours(o[0],o[1],e);for(let o=0;o<2;o++)for(let n=0;n<2;n++)s.add(this._key(t.i0+o,t.j0+n,e).key)}return s}_fetch(t){const e=t.split("/"),s=this.tileUrl(+e[0],+e[1],+e[2]);return new Promise(t=>{const e=new Image;e.crossOrigin="anonymous",e.onload=()=>{try{const s=this.cfg.tileSize,o=document.createElement("canvas");o.width=s,o.height=s;const n=o.getContext("2d",{willReadFrequently:!0});n.drawImage(e,0,0,s,s),t(n.getImageData(0,0,s,s).data)}catch(e){t(null)}},e.onerror=()=>t(null),e.src=s})}load(t){const e=Array.from(t).filter(t=>!this.tiles.has(t));let s=0,o=!0;const n=()=>{if(s>=e.length)return Promise.resolve();const t=e[s++];return this._fetch(t).then(e=>(this.tiles.set(t,e),e||(o=!1),n()))},i=[];for(let t=0;t<Math.min(this.cfg.concurrency,e.length);t++)i.push(n());return Promise.all(i).then(()=>o)}}class F extends t{constructor(t){const e=f(d,t||{});-1===u.indexOf(e.position)&&(e.position="bottom");const s=e.labels;e.labels=m(e.lang,s);const o=function(t){const e=document.createElement("div");return e.className=`ol-elevation-profile ol-unselectable ol-control oep-pos-${t.position} oep-theme-${"string"==typeof t.theme?t.theme:"custom"}`+("floating"===t.immersion?" oep-floating":""),e}(e);super({element:o,target:t&&t.target}),this.options=e,this._userLabels=s,this.slopeColors=e.slopeColors||null,this._feature=null,this._fullSamples=null,this._fullStats=null,this._samples=null,this._stats=null,this._marker=null,this._collapsed=!!e.collapsed,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._demZ=null,this._demFor=null,this._demSeq=0,this._demLoading=!1,this._trackLines=null,this._linesFor=null,this._onResize=()=>{this._feature&&!this._collapsed&&this._render()},this._buildDom(o),o.style.display="none"}get _cropMode(){return this._crops.length>0}get _cropDepth(){return this._crops.length}get _cropMax(){const t=this.options.zoomLevels;return null==t?3:Math.max(1,0|t)}static featureHasZ(t){const e=t&&t.getGeometry&&t.getGeometry();if(!e)return!1;for(const t of y(e))for(const e of t)if(e.length>2&&isFinite(e[2]))return!0;return!1}static featureHasTime(t){const e=t&&t.getGeometry&&t.getGeometry();return!!e&&!!x(t,y(e))}_buildDom(t){const e=this.options;this._applyTheme(),this._applyTransparency();const s=document.createElement("div");s.className="oep-header",this._titleEl=document.createElement("span"),this._titleEl.className="oep-title",this._titleEl.textContent=e.labels.empty,this._statsEl=document.createElement("span"),this._statsEl.className="oep-stats",s.appendChild(this._titleEl),s.appendChild(this._statsEl),this._toolbar=document.createElement("span"),this._toolbar.className="oep-toolbar";const o=(t,e,s,o)=>{const n=document.createElement("button");return n.type="button",n.className=`oep-tbtn ${t}`,n.innerHTML=e,n.title=s,n.setAttribute("aria-label",s),n.addEventListener("click",o),this._toolbar.appendChild(n),n};this._btnA=o("oep-a",'<svg viewBox="0 0 24 24"><path d="M7 5v14M11 12h8m0 0-3-3m3 3-3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomStart,()=>this._arm("A")),this._btnB=o("oep-b",'<svg viewBox="0 0 24 24"><path d="M17 5v14M13 12H5m0 0 3-3m-3 3 3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomEnd,()=>this._arm("B")),this._btnBack=o("oep-back",'<svg viewBox="0 0 24 24"><path d="M10 6 4 12l6 6M4 12h10a6 6 0 0 1 6 6" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomBack,()=>this._popCrop()),this._btnAll=o("oep-all",'<svg viewBox="0 0 24 24"><path d="M4 12h16M4 12l4-4M4 12l4 4M20 12l-4-4M20 12l-4 4" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomAll,()=>this._exitZoom()),this._btnPng=o("oep-png",'<svg viewBox="0 0 24 24"><path d="M12 4v10m0 0 4-4m-4 4-4-4M5 18h14" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.exportPng,()=>this.exportPNG()),s.appendChild(this._toolbar);const n=document.createElement("button");n.className="oep-toggle",n.type="button",n.innerHTML=this._collapsed?M:E,n.addEventListener("click",()=>this.toggleCollapsed()),s.appendChild(n),this._toggleBtn=n,this._applyToggleLabel(),this._legendEl=document.createElement("div"),this._legendEl.className="oep-legend",this._legendEl.style.display="none",this._body=document.createElement("div"),this._body.className="oep-body",t.appendChild(s),t.appendChild(this._legendEl),t.appendChild(this._body),this._applyCollapsable(),this._updateZoomButtons(),this._collapsed&&t.classList.add("oep-collapsed")}_applyLabels(){const t=this.options.labels,e=(t,e)=>{t&&e&&(t.title=e,t.setAttribute("aria-label",e))};e(this._btnA,t.zoomStart),e(this._btnB,t.zoomEnd),e(this._btnBack,t.zoomBack),e(this._btnAll,t.zoomAll),e(this._btnPng,t.exportPng),this._applyToggleLabel(),this._titleEl&&!this._feature&&(this._titleEl.textContent=t.empty)}_applyToggleLabel(){const t=this.options.labels,e=this._collapsed?t.expand:t.collapse;this._toggleBtn&&e&&(this._toggleBtn.title=e,this._toggleBtn.setAttribute("aria-label",e))}_resolveColor(){const t=this.options;return t.color?"auto"===t.color?this._featureColor():t.color:null}_featureColor(){const t=this._feature;if(!t)return null;const e=this.getMap()?this.getMap().getView().getResolution():1;let s=b(t.getStyle&&t.getStyle(),t,e);return!s&&this.options.trackLayer&&(s=b(this.options.trackLayer.getStyle&&this.options.trackLayer.getStyle(),t,e)),function(t){if(null==t)return null;if("string"==typeof t)return t;if(Array.isArray(t)){const e=t.length>3?t[3]:1;return`rgba(${0|t[0]},${0|t[1]},${0|t[2]},${e})`}return null}(s)}_applyTheme(){const t=this.options,e="object"==typeof t.theme?t.theme:c[t.theme]||c.steelblue;this.themeColors=e;const s=this.element,o=this._resolveColor(),n=o||e.area;let i=e.line;if(o)try{i=String(h.color(o).darker(.7))}catch(t){i=o}s.style.setProperty("--oep-area",n),s.style.setProperty("--oep-line",i),s.style.setProperty("--oep-axis",e.axis),s.style.setProperty("--oep-text",e.text),s.style.setProperty("--oep-focus",e.focus)}_applyTransparency(){const t=this.options.transparency;let e;e=!1===t||null==t?1:!0===t?this.options.transparencyLevel:Math.max(0,Math.min(1,+t)),this.element.style.setProperty("--oep-bg",`rgba(255,255,255,${e})`),this.element.classList.toggle("oep-transparent",e<1)}_applyCollapsable(){const t=this.options.collapsable;this._toggleBtn.style.display=t?"":"none",!t&&this._collapsed&&this.toggleCollapsed(!1)}toggleCollapsed(t){this._collapsed="boolean"==typeof t?t:!this._collapsed,this.element.classList.toggle("oep-collapsed",this._collapsed),this._toggleBtn.innerHTML=this._collapsed?M:E,this._applyToggleLabel(),!this._collapsed&&this._feature&&this._render(),this._adjustAttribution()}_availWidth(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement();return e&&e.clientWidth||("undefined"!=typeof window?window.innerWidth:1024)}_isMobile(){return this.options.responsive&&"undefined"!=typeof window&&window.innerWidth<=(this.options.mobileBreakpoint||640)}_applyPlacement(){const t=this._isMobile();let e=this.options.position;return t&&(e=/top/.test(e)?"top":"bottom"),this.element.className=this.element.className.replace(/oep-pos-\S+/,`oep-pos-${e}`),this.element.classList.toggle("oep-mobile",t),t}_adjustAttribution(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement(),s=e&&e.querySelector&&e.querySelector(".ol-attribution");if(!s)return;if(s.style.bottom="",s.style.right="","none"===this.element.style.display||this._collapsed)return;const o=e.getBoundingClientRect(),n=this.element.getBoundingClientRect();if(!n.height)return;const i=o.bottom-n.bottom,l=o.right-n.right;i<n.height&&l<24&&(s.style.right=`${Math.max(0,Math.round(l))}px`,s.style.bottom=`${Math.round(n.height+2*i)}px`)}setMap(t){const o=this.getMap();if(super.setMap(t),this._mapKeys&&(this._mapKeys.forEach(s.unByKey),this._mapKeys=null),o&&"undefined"!=typeof window&&window.removeEventListener("resize",this._onResize),this._marker&&!t&&this._marker.setPosition(void 0),!t)return;const n=this.options;if(n.dataProjection||(n.dataProjection=t.getView().getProjection()),n.marker&&!this._marker){const s=document.createElement("div");s.className="oep-marker",this._marker=new e({element:s,positioning:"center-center",stopEvent:!1}),t.addOverlay(this._marker)}"undefined"!=typeof window&&window.addEventListener("resize",this._onResize);const i=e=>t.forEachFeatureAtPixel(e,t=>{const e=t.getGeometry();return(s=e)&&/^(Multi)?(LineString|Polygon)$|^LinearRing$/.test(s.getType())?t:void 0;var s});this._mapKeys=[],this._mapKeys.push(t.on("click",t=>{const e=i(t.pixel);"mouseover"!==this.options.show&&e&&e!==this._feature&&this.setFeature(e),this.options.hideOnMapClick&&!e&&this._feature&&this.clear()})),this._mapKeys.push(t.on("pointermove",e=>{if("mouseover"===this.options.show){const t=i(e.pixel);t&&t!==this._feature&&this.setFeature(t)}if(!this.options.followMap||!this._feature||this._collapsed)return;const s=this._closestOnProfile(e.coordinate);if(!s)return;const o=t.getPixelFromCoordinate(s);o&&(Math.hypot(o[0]-e.pixel[0],o[1]-e.pixel[1])<14?this._focusByCoord(s):this._clearFocus())})),this._mapKeys.push(t.on("moveend",()=>{const e=this._crops[this._crops.length-1];e&&e.fitRes&&t.getView().getResolution()>1.25*e.fitRes&&this._popCrop()})),this._mapKeys.push(t.on("change:size",this._onResize))}setFeature(t){return this._feature=t||null,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,t?(this.element.style.display="",this._compute(),this._fillFromDem(t),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render(),this):(this._fullSamples=this._samples=null,this._demZ=this._demFor=null,this._trackLines=this._linesFor=null,this._clear(),this)}clear(){return this.setFeature(null)}getStats(){return this._stats}setTheme(t){return this.options.theme=t,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setColor(t){return this.options.color=t||null,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setOptions(t){return this.options=f(this.options,t||{}),t&&"slopeColors"in t&&(this.slopeColors=t.slopeColors||null),t&&(t.theme||"color"in t)&&this._applyTheme(),t&&("transparency"in t||"transparencyLevel"in t)&&this._applyTransparency(),t&&"collapsable"in t&&this._applyCollapsable(),t&&"labels"in t&&(this._userLabels=f(this._userLabels||{},t.labels)),t&&("lang"in t||"labels"in t)&&(this.options.labels=m(this.options.lang,this._userLabels),this._applyLabels()),t&&("zoom"in t||"exportPng"in t)&&this._updateZoomButtons(),t&&void 0!==t.width&&"number"==typeof t.width&&(this.options.width=t.width),t&&"dem"in t&&(this._demZ=null,this._demFor=null,this._trackLines=null,this._linesFor=null),this._feature&&(this._compute(),this._fillFromDem(this._feature),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render()),this}_fillFromDem(t){const e=function(t){if(!t)return null;if("function"==typeof t)return Object.assign({},C,{sample:t});const e=!0===t||"string"==typeof t?{source:!0===t?"terrarium":t}:Object.assign({},t);if("function"==typeof e.sample)return Object.assign({},C,e);if(e.track){const t=Object.assign({},C,e);return t.track=Object.assign({coords:"coords",parse:null,fetchOptions:null},"string"==typeof e.track?{url:e.track}:e.track),t.track.url?t:null}if(e.featureInfo){const t=Object.assign({},C,e);return t.sample=$(t),t}if(e.olSource&&"function"!=typeof e.olSource.getTileUrlFunction&&"function"==typeof e.olSource.getTile){const t=Object.assign({},C,e);return t.sample=L(t),t}const s=e.url||e.wms||e.olSource,o=w[e.source]||(s?{}:w.terrarium),n=Object.assign({},C,o,e);return"ign"===n.api?(n.sample=z(n),n):n.url||n.wms||n.olSource?n:null}(this.options.dem);if(!e||!t||this._demFor===t||this._linesFor===t)return;if(F.featureHasZ(t))return;if(!e.sample&&("undefined"==typeof Image||"undefined"==typeof document))return;const s=t.getGeometry&&t.getGeometry(),n=s?y(s):[],i=this.options.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=[];for(const t of n)for(const e of t)l.push(o.toLonLat(e,i));if(!l.length&&!e.track)return;const r=++this._demSeq;this._demLoading=!0;try{this._startFill(e,r,t,l,i)}catch(e){this._demDone(r,t,null,l.length,null,0)}}_startFill(t,e,s,o,n){if(t.track)return void this._startTrackFill(t,e,s,o.length,n);if(t.sample)return void Promise.resolve().then(()=>t.sample(o,{feature:s,projection:n})).then(t=>this._demDone(e,s,t,o.length,null,0)).catch(()=>this._demDone(e,s,null,o.length,null,0));const i=new B(t),l=function(t,e,s){if("number"==typeof s.zoom)return s.zoom;for(let o=s.maxZoom;o>0;o--)if(t.tilesFor(e,o).size<=s.maxTiles)return o;return 1}(i,o,t);i.load(i.tilesFor(o,l)).then(t=>{const n=t?o.map(t=>i.sample(t[0],t[1],l)):null;this._demDone(e,s,n,o.length,l,i.tiles.size)}).catch(()=>this._demDone(e,s,null,o.length,l,0))}_startTrackFill(t,e,s,o,n){const i=function(t,e){if("function"==typeof t)return t(e)||null;if("string"!=typeof t||!e)return null;let s=!0;const o=t.replace(/\{(\w+)\}/g,(t,o)=>{const n=e.get(o);return null==n||""===n?(s=!1,""):encodeURIComponent(String(n))});return s?o:null}(t.track.url,s);i?Promise.resolve().then(()=>fetch(i,t.track.fetchOptions||void 0)).then(t=>{if(!t.ok)throw new Error(String(t.status));return t.json()}).then(i=>{const l=t.track.parse?t.track.parse(i,s):Array.isArray(i)?i:i&&i[t.track.coords];this._trackDone(e,s,l,o,n)}).catch(()=>this._demDone(e,s,null,o,null,0)):this._demDone(e,s,null,o,null,0)}_trackDone(t,e,s,n,i){const l=()=>this._demDone(t,e,null,n,null,0);if(!Array.isArray(s)||!s.length)return l();if("number"==typeof s[0])return void this._demDone(t,e,s,n,null,0);if(t!==this._demSeq||this._feature!==e)return;const r=t=>null!=t&&isFinite(t),a=[];for(const t of s){if(!t||t.length<3||!r(t[0])||!r(t[1])||!r(t[2]))return l();const e=o.transform([t[0],t[1]],"EPSG:4326",i);a.push([e[0],e[1],t[2]])}if(a.length<2)return l();this._demLoading=!1,this._trackLines=[a],this._linesFor=e,this._demZ=null,this._demFor=null,this._compute(),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:!0,zoom:null,tiles:0})}_demDone(t,e,s,o,n,i){if(t!==this._demSeq||this._feature!==e)return;const l=Array.isArray(s)&&s.length===o&&s.every(t=>null!=t&&isFinite(t));this._demLoading=!1,l&&(this._demZ=s,this._demFor=e,this._compute()),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:l,zoom:n,tiles:i})}_compute(){const t=this.options,e=this._linesFor===this._feature&&this._trackLines,s=this._feature.getGeometry&&this._feature.getGeometry(),n=e?this._trackLines:s?y(s):[],l=t.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",r=this._demFor===this._feature?this._demZ:null,a=e?null:x(this._feature,n);this._hasTime=!!a;const h=!1!==t.ignoreStops,c=null!=t.stopSpeed?t.stopSpeed:.5,u=[];let p=0,d=null,m=-1,f=0,_=null;for(const t of n)for(const e of t){m++;const t=o.toLonLat(e,l);let s=0;d&&(s=i.getDistance(d,t),p+=s);let n=null;if(a&&null!=a[m]){const t=a[m];if(null!=_){const e=(t-_)/1e3;e>0&&(!h||s/e>=c)&&(f+=e)}n=f,_=t}d=t;const g=e.length>2&&isFinite(e[2])?e[2]:r?r[m]:0;u.push({x:p,z:g,coord:e,t:n})}t.smoothing>0&&this._smooth(u,t.smoothing);const g=this._decimate(u,t.maxPoints);this._addSlope(g),this._fullSamples=g,this._fullStats=this._statsOf(g,!0),this._applyCrops()}_pxPerCm(){try{const t=document.createElement("div");t.style.cssText="position:absolute;left:-9999px;top:0;width:1cm;height:1cm",(this.element||document.body).appendChild(t);const e=t.getBoundingClientRect().height;if(t.remove(),e>0)return e}catch(t){}return 96/2.54}_yScale(t,e,s,o){const n=t.min-e,i=t.max+e,l=s/this._pxPerCm(),r=o/this._pxPerCm(),a=e=>r>0&&e>0?t.distance/r/(e/l):null,c=this._verticalScaleFor(t,o);if(!(c>0)){const t=h.scaleLinear().domain([n,i]).range([s,0]).nice(),e=t.domain();return this._vScale=null,this._vExaggeration=a(e[1]-e[0]),t}const u=Math.max(c*l,i-n),p=(n+i)/2;return this._vScale=u/l,this._vExaggeration=a(u),h.scaleLinear().domain([p-u/2,p+u/2]).range([s,0])}_verticalScaleFor(t,e){const s=this.options.verticalScale;if("number"==typeof s)return s;const o=s&&"object"==typeof s?Number(s.exaggeration):0;if(!(o>0&&t.distance>0&&e>0))return 0;const n=e/this._pxPerCm();return t.distance/n/o}_statsOf(t,e){let s=0,o=0,n=1/0,i=-1/0,l=0;for(let e=0;e<t.length;e++){const r=t[e].z;if(r<n&&(n=r),r>i&&(i=r),e>0){const n=r-t[e-1].z;n>0?s+=n:o-=n}const a=Math.abs(t[e].slope||0);a>l&&(l=a)}const r=t.length?t[t.length-1].x-t[0].x:0,a=t.length?t[0].t:null,h=t.length?t[t.length-1].t:null;return{distance:r,duration:null!=a&&null!=h?h-a:null,ascent:s,descent:o,min:isFinite(n)?n:0,max:isFinite(i)?i:0,maxAbsSlope:l,points:t.length}}_smooth(t,e){if(!(e>0)||t.length<3)return;const s=e/2,o=t.map(t=>t.z);let n=0,i=0,l=0;for(let e=0;e<t.length;e++){const r=t[e].x;for(;n<t.length&&t[n].x<r-s;)l-=o[n],n++;for(;i<t.length&&t[i].x<=r+s;)l+=o[i],i++;t[e].z=i>n?l/(i-n):o[e]}}_decimate(t,e){const s=t=>({x:t.x,z:t.z,coord:t.coord,t:t.t});if(!e||t.length<=e)return t.map(s);const o=t.length/e,n=[];for(let i=0;i<e;i++)n.push(s(t[Math.floor(i*o)]));return n.push(s(t[t.length-1])),n}_addSlope(t){for(let e=1;e<t.length;e++){const s=t[e].x-t[e-1].x;t[e].slope=s>0?(t[e].z-t[e-1].z)/s*100:0}t.length&&(t[0].slope=t.length>1?t[1].slope:0)}_slopeScale(){const t=this.options.slopeClassSize||2.5,e=this.options.maxClasses||8,s=Math.max(1,Math.floor((this._stats.maxAbsSlope||0)/t)),o=Math.min(s,e-1),n=s>o;let i;if(this.slopeColors&&this.slopeColors.length){const t=h.interpolateRgbBasis(this.slopeColors);i=e=>t(o?e/o:0)}else{const t=h.scaleLinear().domain([0,.16,.42,.68,1]).range(["#2166ac","#27a35a","#ffe000","#f4791f","#d7191c"]).interpolate(h.interpolateRgb).clamp(!0);i=e=>String(t(o?e/o:0))}return{classSize:t,maxIdx:o,capped:n,colorByIndex:i}}_classIndex(t,e){return Math.min(e.maxIdx,Math.floor(Math.abs(t)/e.classSize))}_fmtDuration(t){if(null==t||!isFinite(t))return"";const e=this.options.labels&&this.options.labels.durationUnits||p.en.durationUnits;if((t=Math.max(0,Math.round(t)))<60)return t+" "+e.s;if(t<3600)return Math.round(t/60)+" "+e.m;if(t<86400){let s=Math.floor(t/3600),o=Math.round(t%3600/60);return 60===o&&(s++,o=0),o?`${s} ${e.h} ${o} ${e.m}`:`${s} ${e.h}`}let s=Math.floor(t/86400),o=Math.round(t%86400/3600);return 24===o&&(s++,o=0),o?`${s} ${e.d} ${o} ${e.h}`:`${s} ${e.d}`}_hasElevation(){const t=this._feature;return!!t&&(!!F.featureHasZ(t)||(!(this._demFor!==t||!this._demZ)||!(this._linesFor!==t||!this._trackLines)))}_renderNoElevation(){if(!this.options.showWithoutElevation)return void(this.element.style.display="none");this.element.style.display="",this._applyTheme(),this._applyPlacement(),this._renderHeader(!0);const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-noelev",e.style.height=`${t}px`,e.setAttribute("role","status"),e.textContent=this.options.labels.noElevation,this._body.appendChild(e),this._clearFocus()}_pickProperty(t,e,s){if(!e||!t||!t.get)return null;for(const o of Array.isArray(e)?e:[e]){const e=t.get(o);if(null!=e&&""!==e&&(!s||s(e)))return e}return null}_renderTitle(){const t=this.options,e=this._feature;if(!e)return;const s=this._pickProperty(e,t.titleProperty)||t.labels.untitled,o=this._pickProperty(e,t.titleLink,g);g(o)?this._titleEl.innerHTML=`<a href="${_(o)}" target="_blank" rel="noopener">${_(s)}</a>`:this._titleEl.textContent=s,this._titleEl.setAttribute("title",s)}_renderHeader(t){const e=this.options,s=this._stats,o=this._feature;if(this._renderTitle(),this._demLoading)return this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._legendEl.innerHTML="",void(this._legendEl.style.display="none");const n=[],i=[];if(e.headerItems.forEach(l=>{if("string"==typeof l){if(t&&("ascent"===l||"descent"===l||"min"===l||"max"===l||"minmax"===l))return;if("distance"===l){if(!(s&&s.distance>0))return;n.push(`<b>${v(s.distance,e.units)}</b>`),i.push(v(s.distance,e.units))}else if("ascent"===l)n.push(`<span class="oep-up">${e.labels.ascent} ${S(s.ascent,e.units)}</span>`),i.push(`${e.labels.ascent} ${S(s.ascent,e.units)}`);else if("descent"===l)n.push(`<span class="oep-down">${e.labels.descent} ${S(s.descent,e.units)}</span>`),i.push(`${e.labels.descent} ${S(s.descent,e.units)}`);else if("min"===l)n.push(S(s.min,e.units)),i.push(S(s.min,e.units));else if("max"===l)n.push(S(s.max,e.units)),i.push(S(s.max,e.units));else if("minmax"===l){const t=`${S(s.min,e.units)}-${S(s.max,e.units)}`;n.push(t),i.push(t)}else if("duration"===l&&null!=s.duration){const t=this._fmtDuration(s.duration);n.push(`<span class="oep-time">${_(e.labels.duration)} ${t}</span>`),i.push(`${e.labels.duration} ${t}`)}}else if(l&&l.property){const t=o.get&&o.get(l.property);if(null==t||""===t)return;const e=l.label?`${l.label} `:"";l.asLink&&g(t)?(n.push(`${e}<a href="${_(t)}" target="_blank" rel="noopener">${_(l.linkText||l.label||t)}</a>`),i.push(`${l.label||""} ${t}`)):(n.push(_(e+t)),i.push(e+t))}}),this._statsEl.innerHTML=n.join(" · "),this._statsEl.setAttribute("title",i.join(" · ")),this._legendEl.innerHTML="",e.slope&&e.slopeLegend){const t=this._slopeScale();for(let e=0;e<=t.maxIdx;e++){const s=t.colorByIndex(e),o=t.capped&&e===t.maxIdx?`≥ ${e*t.classSize} %`:`${e*t.classSize}-${(e+1)*t.classSize} %`,n=document.createElement("span");n.className="oep-leg-it",n.innerHTML=`<i class="oep-sw" style="background:${s}"></i>${o}`,this._legendEl.appendChild(n)}this._legendEl.style.display=""}else this._legendEl.style.display="none"}_renderSpinner(){const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-loading",e.style.height=`${t}px`,e.setAttribute("role","status"),e.setAttribute("aria-label",this.options.labels.loading);const s=document.createElement("div");s.className="oep-spinner",e.appendChild(s),this._body.appendChild(e)}_render(){const t=this.options,e=this._stats,s=this._samples;if(!this._demLoading&&!this._hasElevation())return void this._renderNoElevation();if(!s||!s.length)return;this._applyTheme();const o=this._applyPlacement();if(this._renderHeader(),this._demLoading)return void this._renderSpinner();const n=t.margins,i=n.unit||"px",l=t=>"px"===i?t:t*(parseFloat(getComputedStyle(this.element).fontSize)||16),r=this._availWidth(),a="auto"===t.width||"100%"===t.width||"full"===t.width?r:Math.min("number"==typeof t.width?t.width:parseFloat(t.width)||r,r);this.element.style.width=o?"":`${a}px`;const c=this.element.clientWidth||(o?r:a),u=Math.max(220,c-16),p="number"==typeof t.height?t.height:180,d=l(n.top),m=l(n.right),f=l(n.bottom),_=l(n.left),g=Math.max(10,u-_-m),y=Math.max(10,p-d-f),x=null!=t.xTicks?t.xTicks:Math.max(2,Math.round(g/80)),b=null!=t.yTicks?t.yTicks:Math.max(2,Math.round(y/40));this._body.innerHTML="";const v=h.select(this._body).append("svg").attr("class","oep-svg").attr("width",u).attr("height",p).attr("viewBox",`0 0 ${u} ${p}`),S=v.append("g").attr("transform",`translate(${_},${d})`),E=h.scaleLinear().domain([0,e.distance]).range([0,g]),M=.1*(e.max-e.min)||10,k=this._yScale(e,M,y,g);this._x=E,this._y=k,this._dims={innerW:g,innerH:y},t.grid&&S.append("g").attr("class","oep-grid").call(h.axisLeft(k).ticks(b).tickSize(-g).tickFormat(""));const w="imperial"===t.units?1609.344:1e3;const z=h.area().x(t=>E(t.x)).y0(y).y1(t=>k(t.z));if(t.slope){const e=this._slopeScale(),o=[];let n=1;for(;n<s.length;){const t=this._classIndex(s[n].slope,e);let i=n;for(;i+1<s.length&&this._classIndex(s[i+1].slope,e)===t;)i++;S.append("path").datum(s.slice(n-1,i+1)).attr("class","oep-area-slope").attr("fill",e.colorByIndex(t)).attr("d",z),n>1&&o.push(s[n-1]),n=i+1}t.slopeSeparators&&o.forEach(t=>{S.append("line").attr("class","oep-slope-sep").attr("x1",E(t.x)).attr("x2",E(t.x)).attr("y1",k(t.z)).attr("y2",y)})}else S.append("path").datum(s).attr("class","oep-area").attr("d",z);S.append("path").datum(s).attr("class","oep-line").attr("d",h.line().x(t=>E(t.x)).y(t=>k(t.z))),S.append("g").attr("class","oep-axis oep-axis-x").attr("transform",`translate(0,${y})`).call(h.axisBottom(E).ticks(x).tickFormat(t=>(t/w).toFixed(t/w<10?1:0))),S.append("text").attr("class","oep-axis-label").attr("x",g).attr("y",y+f-4).attr("text-anchor","end").text((t=>"imperial"===t?"mi":"km")(t.units)),S.append("g").attr("class","oep-axis oep-axis-y").call(h.axisLeft(k).ticks(b).tickFormat(e=>"imperial"===t.units?Math.round(3.28084*e):e)),t.zoom&&this._cropDepth<this._cropMax&&[["A",this._zoomA],["B",this._zoomB]].forEach(([t,e])=>{if(null==e)return;const s=E(e);S.append("line").attr("class","oep-ab-line").attr("x1",s).attr("x2",s).attr("y1",0).attr("y2",y),S.append("text").attr("class","oep-ab-label").attr("x",s).attr("y",-6).attr("text-anchor","middle").text(t)});const C=S.append("g").attr("class","oep-focus").style("display","none");C.append("line").attr("class","oep-focus-line").attr("y1",0).attr("y2",y),C.append("circle").attr("class","oep-focus-dot").attr("r",4);const P=C.append("g").attr("class","oep-focus-label");P.append("rect").attr("class","oep-focus-bg"),P.append("text").attr("class","oep-focus-txt"),this._focus=C;const T=t=>{const s=h.pointer(t,S.node())[0];return Math.max(0,Math.min(e.distance,E.invert(s)))},j=v.append("rect").attr("class","oep-overlay").attr("x",_).attr("y",d).attr("width",g).attr("height",y);j.on("mousemove",t=>{const e=this._sampleAt(T(t));e&&(this._setFocus(e),this._marker&&this._marker.setPosition(e.coord))}).on("mouseout",()=>this._clearFocus()),j.on("click",t=>this._placeBound(T(t))),this._armed&&j.style("cursor","col-resize"),this._adjustAttribution()}static get _EXPORT_PROPS(){return["fill","fill-opacity","stroke","stroke-width","stroke-dasharray","stroke-linecap","stroke-linejoin","opacity","font-family","font-size","font-weight","text-anchor","shape-rendering"]}_freezeStyles(t,e){const s=F._EXPORT_PROPS,o=getComputedStyle(t);let n="";for(const t of s){const e=o.getPropertyValue(t);e&&(n+=`${t}:${e};`)}e.setAttribute("style",n);const i=t.children,l=e.children;for(let t=0;t<i.length&&t<l.length;t++)this._freezeStyles(i[t],l[t])}_exportSvg(){const t=this._body.querySelector("svg");if(!t)return null;const e=getComputedStyle(this.element),s=e.getPropertyValue("--oep-bg").trim()||"#fff",o=e.getPropertyValue("--oep-text").trim()||"#222",n=e.fontFamily||"system-ui, sans-serif",i=+t.getAttribute("width"),l=+t.getAttribute("height"),r=this._statsEl.textContent?15:0,a="none"!==this._legendEl.style.display?this._legendEl:null,h=28+r+(a?18:0),c=t.cloneNode(!0);c.querySelectorAll(".oep-focus, .oep-overlay").forEach(t=>t.remove()),this._freezeStyles(t,c);const u=t=>_(String(t)),p=[];if(p.push(`<rect width="${i+16}" height="${l+h+8}" fill="${u(s)}"/>`),p.push(`<text x="8" y="21" style="font-family:${u(n)};font-size:13px;font-weight:600;fill:${u(o)}">${u(this._titleEl.textContent)}</text>`),r&&p.push(`<text x="8" y="38" style="font-family:${u(n)};font-size:11px;fill:${u(o)};opacity:.85">${u(this._statsEl.textContent)}</text>`),a){let t=8;const e=28+r+12;for(const s of a.querySelectorAll(".oep-leg-it")){const i=s.querySelector(".oep-sw"),l=i?getComputedStyle(i).backgroundColor:"none",r=s.textContent.trim();p.push(`<rect x="${t}" y="${e-8}" width="10" height="10" fill="${u(l)}"/>`),p.push(`<text x="${t+14}" y="${e}" style="font-family:${u(n)};font-size:10px;fill:${u(o)}">${u(r)}</text>`),t+=14+5.6*r.length+10}}return p.push(`<g transform="translate(8,${h})">${(new XMLSerializer).serializeToString(c)}</g>`),{width:i+16,height:l+h+8,svg:`<svg xmlns="http://www.w3.org/2000/svg" width="${i+16}" height="${l+h+8}" viewBox="0 0 ${i+16} ${l+h+8}">${p.join("")}</svg>`}}exportPNG(t){const e=t||{},s=this._exportSvg();if(!s)return Promise.reject(new Error("ol-elevation-profile: nothing to export"));const o=e.scale||"undefined"!=typeof window&&window.devicePixelRatio||1;return new Promise((t,n)=>{const i=new Image;i.onload=()=>{try{const l=document.createElement("canvas");l.width=Math.round(s.width*o),l.height=Math.round(s.height*o);const r=l.getContext("2d");r.scale(o,o),r.drawImage(i,0,0),l.toBlob(s=>{s?(!1!==e.download&&this._save(s,e.filename),t(s)):n(new Error("ol-elevation-profile: PNG encoding failed"))},"image/png")}catch(t){n(t)}},i.onerror=()=>n(new Error("ol-elevation-profile: SVG could not be rasterised")),i.src="data:image/svg+xml;charset=utf-8,"+encodeURIComponent(s.svg)})}_save(t,e){const s=e||`${(this._titleEl.textContent||"profile").replace(/[\\/:*?"<>|]+/g,"-").trim()}.png`,o=URL.createObjectURL(t),n=document.createElement("a");n.href=o,n.download=s,document.body.appendChild(n),n.click(),n.remove(),setTimeout(()=>URL.revokeObjectURL(o),1e3)}_arm(t){this._armed=this._armed===t?null:t,this._updateZoomButtons(),this._focus&&this._render()}_placeBound(t){if(!this._armed||this._cropDepth>=this._cropMax)return;const e="A"===this._armed?"B":"A";"A"===this._armed?this._zoomA=t:this._zoomB=t;const s=null!=this._zoomA&&null!=this._zoomB;this._armed=s?null:e,this._updateZoomButtons(),s?this._pushCrop(this._zoomA,this._zoomB):this._render()}_updateZoomButtons(){const t=this.options,e=!!this._feature,s=!!t.zoom&&e,o=!!t.exportPng&&e;this._toolbar.style.display=s||o?"":"none",this._btnPng.style.display=o?"":"none";const n=this._cropDepth,i=n<this._cropMax;this._btnA.style.display=s&&i?"":"none",this._btnB.style.display=s&&i?"":"none",this._btnBack.style.display=s&&n>1?"":"none",this._btnAll.style.display=s&&n>0?"":"none",this._btnA.classList.toggle("armed","A"===this._armed),this._btnB.classList.toggle("armed","B"===this._armed)}_applyCrops(){if(!this._crops.length)return this._off=0,this._samples=this._fullSamples,this._stats=this._fullStats,null;const{a:t,b:e}=this._crops[this._crops.length-1],s=this._fullSamples.filter(s=>s.x>=t&&s.x<=e);if(s.length<2)return this._crops.pop(),this._applyCrops();const o=s[0].x,n=null!=s[0].t?s[0].t:0;return this._off=o,this._samples=s.map(t=>({x:t.x-o,z:t.z,coord:t.coord,slope:t.slope,t:null!=t.t?t.t-n:null})),this._stats=this._statsOf(this._samples,!1),s.map(t=>t.coord)}_fitMap(t){const e=this.getMap();if(!e)return null;let s=null;if(t&&t.length?s=l.boundingExtent(t):this._feature&&(s=this._feature.getGeometry().getExtent()),!s)return null;const o=e.getView();let n=null;try{n=o.getResolutionForExtent(s,e.getSize())}catch(t){n=null}return o.fit(s,{padding:[40,40,40,40],duration:400}),n}_pushCrop(t,e){if(this._zoomA=null,this._zoomB=null,this._armed=null,this._cropDepth>=this._cropMax)return this._updateZoomButtons(),void this._render();const s=this._off+Math.min(t,e),o=this._off+Math.max(t,e);let n=0;for(let t=0;t<this._fullSamples.length;t++){const e=this._fullSamples[t].x;e>=s&&e<=o&&n++}if(n<2)return this._updateZoomButtons(),void this._render();this._crops.push({a:s,b:o,fitRes:null});const i=this._applyCrops();this._updateZoomButtons(),this._render();const l=this._crops[this._crops.length-1];l&&(l.fitRes=this._fitMap(i))}_applyZoom(){null!=this._zoomA&&null!=this._zoomB&&this._pushCrop(this._zoomA,this._zoomB)}_popCrop(){if(!this._crops.length)return;this._crops.pop(),this._zoomA=null,this._zoomB=null,this._armed=null;const t=this._applyCrops();this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(t)}_exitZoom(){this._crops.length=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._applyCrops(),this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(null)}_closestOnProfile(t){const e=this._feature&&this._feature.getGeometry();if(!e)return null;if(!/Polygon/.test(e.getType()))return e.getClosestPoint(t);const s=this._projectOn(this._fullSamples,t);return s?s.coord:null}_projectOn(t,e){if(!t||!t.length)return null;if(1===t.length)return{x:t[0].x,coord:t[0].coord.slice(0,2)};let s=null,o=1/0;for(let n=1;n<t.length;n++){const i=t[n-1].coord,l=t[n].coord,r=l[0]-i[0],a=l[1]-i[1],h=r*r+a*a;let c=h>0?((e[0]-i[0])*r+(e[1]-i[1])*a)/h:0;c=c<0?0:c>1?1:c;const u=i[0]+r*c,p=i[1]+a*c,d=u-e[0],m=p-e[1],f=d*d+m*m;f<o&&(o=f,s={x:t[n-1].x+(t[n].x-t[n-1].x)*c,coord:[u,p]})}return s}_tooltipText(t){const e=this.options,s=[];return e.tooltipItems.forEach(o=>{var n;"distance"===o?s.push(v(t.x,e.units)):"elevation"===o?s.push(S(t.z,e.units)):"slope"===o?s.push(`${(n=t.slope||0)>=0?"+":""}${n.toFixed(1)} %`):"time"===o&&null!=t.t&&s.push(this._fmtDuration(t.t))}),s.join(" · ")}_setFocus(t){if(!this._focus)return;const e=this._x,s=this._y;this._focus.style("display",null),this._focus.select(".oep-focus-line").attr("x1",e(t.x)).attr("x2",e(t.x)),this._focus.select(".oep-focus-dot").attr("cx",e(t.x)).attr("cy",s(t.z));let o=s(t.z)-16;o<12&&(o=s(t.z)+22);const n=this._focus.select(".oep-focus-txt").attr("x",e(t.x)).attr("y",o).text(this._tooltipText(t)),i=n.node().getBBox();this._focus.select(".oep-focus-bg").attr("x",i.x-4).attr("y",i.y-2).attr("width",i.width+8).attr("height",i.height+4),e(t.x)+i.width/2>this._dims.innerW?n.attr("text-anchor","end"):e(t.x)-i.width/2<0?n.attr("text-anchor","start"):n.attr("text-anchor","middle")}_sampleAt(t){const e=this._samples;if(!e||!e.length)return null;if(1===e.length)return e[0];const s=e[0].x,o=e[e.length-1].x,n=Math.max(s,Math.min(o,t)),i=Math.min(Math.max(k(e,n,1),1),e.length-1),l=e[i-1],r=e[i],a=r.x-l.x,h=a>0?(n-l.x)/a:0,c=(t,e)=>t+(e-t)*h;return{x:n,z:c(l.z,r.z),coord:[c(l.coord[0],r.coord[0]),c(l.coord[1],r.coord[1])],slope:r.slope,t:null!=l.t&&null!=r.t?c(l.t,r.t):null}}_focusByCoord(t){const e=this._projectOn(this._samples,t);if(!e)return;const s=this._sampleAt(e.x);s&&(this._setFocus(s),this._marker&&this._marker.setPosition(s.coord))}_clearFocus(){this._focus&&this._focus.style("display","none"),this._marker&&this._marker.setPosition(void 0)}_clear(){this._body.innerHTML="",this._legendEl.innerHTML="",this._legendEl.style.display="none",this._titleEl.textContent=this.options.labels.empty,this._titleEl.removeAttribute("title"),this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._crops=[],this._off=0,this._demLoading=!1,this._updateZoomButtons(),this._clearFocus(),this.element.style.display="none",this._adjustAttribution()}}return F.addTheme=(t,e)=>{c[t]=e},F.THEMES=c,F.DEM_PRESETS=w,F.DemSampler=B,F.POSITIONS=u,F.version="2.1.0",F});
|
|
18
|
+
*/const c={steelblue:{area:"#4682b4",line:"#3a6d96",axis:"#555",text:"#222",focus:"#e6550d"},lime:{area:"#9ccc2f",line:"#7da521",axis:"#555",text:"#222",focus:"#d62728"},purple:{area:"#9467bd",line:"#76529c",axis:"#555",text:"#222",focus:"#ff9f1c"},slate:{area:"#7c8a99",line:"#4a5560",axis:"#5a6570",text:"#26303a",focus:"#2f81f7"},graphite:{area:"#9a948c",line:"#5c574f",axis:"#5c574f",text:"#2b2823",focus:"#e07a3f"},amber:{area:"#f0a23b",line:"#c4671a",axis:"#7a5a36",text:"#3a2a16",focus:"#1f6fb2"}},u=["top","bottom","left","right","top-left","top-right","bottom-left","bottom-right"],p={en:{distance:"Distance",elevation:"Elevation",slope:"Slope",ascent:"D+",descent:"D-",empty:"Click a track",noElevation:"No elevation data",untitled:"Profile",time:"Time",duration:"Duration",durationUnits:{s:"sec",m:"min",h:"h",d:"d"},zoomStart:"Set start (A)",zoomEnd:"Set end (B)",zoomAll:"Show all",zoomBack:"Back one level",exportPng:"Export as PNG",collapse:"Collapse the profile",expand:"Expand the profile",loading:"Loading the elevation profile"},fr:{distance:"Distance",elevation:"Altitude",slope:"Pente",ascent:"D+",descent:"D-",empty:"Cliquez un tracé",noElevation:"Aucune altimétrie",untitled:"Profil",time:"Temps",duration:"Durée",durationUnits:{s:"sec",m:"min",h:"h",d:"j"},zoomStart:"Définir le début (A)",zoomEnd:"Définir la fin (B)",zoomAll:"Tout voir",zoomBack:"Revenir au niveau précédent",exportPng:"Exporter en PNG",collapse:"Réduire le profil",expand:"Agrandir le profil",loading:"Chargement du profil altimétrique"},es:{distance:"Distancia",elevation:"Altitud",slope:"Pendiente",ascent:"D+",descent:"D-",empty:"Haga clic en una traza",noElevation:"Sin datos de altitud",untitled:"Perfil",time:"Tiempo",duration:"Duración",durationUnits:{s:"seg",m:"min",h:"h",d:"d"},zoomStart:"Definir el inicio (A)",zoomEnd:"Definir el final (B)",zoomAll:"Ver todo",zoomBack:"Volver al nivel anterior",exportPng:"Exportar como PNG",collapse:"Contraer el perfil",expand:"Desplegar el perfil",loading:"Cargando el perfil de elevación"}},d={immersion:"docked",position:"bottom",width:520,height:180,margins:{unit:"px",top:20,right:24,bottom:30,left:48},units:"meters",dataProjection:null,dem:"terrarium",maxPoints:2e3,smoothing:0,theme:"steelblue",color:null,trackLayer:null,transparency:!1,transparencyLevel:.45,grid:!0,slope:!1,slopeClassSize:2.5,slopeColors:null,slopeSeparators:!0,slopeLegend:!0,maxClasses:8,xTicks:null,yTicks:null,verticalScale:"auto",show:"click",showWithoutElevation:!0,collapsable:!0,collapsed:!1,followMap:!0,marker:!0,hideOnMapClick:!0,responsive:!0,mobileBreakpoint:640,zoom:!1,zoomLevels:3,exportPng:!1,ignoreStops:!0,stopSpeed:.5,tooltipItems:["distance","elevation"],headerItems:["distance","ascent","descent","minmax"],titleProperty:"name",titleLink:null,lang:"en",labels:{}};function m(t,e){return f(p[t]||p.en,e||null)}function f(t,e){const s={};return Object.keys(t).forEach(e=>{s[e]=t[e]}),e&&Object.keys(e).forEach(o=>{e[o]&&"object"==typeof e[o]&&!Array.isArray(e[o])&&t[o]&&"object"==typeof t[o]?s[o]=f(t[o],e[o]):s[o]=e[o]}),s}const _=t=>String(t).replace(/[&<>"']/g,t=>({"&":"&","<":"<",">":">",'"':""","'":"'"}[t])),g=t=>"string"==typeof t&&/^(https?:)?\/\/|^mailto:/i.test(t);function y(t){if(!t||!t.getCoordinates)return[];const e=t.getCoordinates();switch(t.getType()){case"LineString":case"LinearRing":return[e];case"MultiLineString":return e;case"Polygon":return e.length?[e[0]]:[];case"MultiPolygon":return e.map(t=>t[0]).filter(Boolean);default:return[]}}function x(t,e){const s=t&&t.getProperties?t.getProperties():{};let o=s.coordTimes;null==o&&s.coordinateProperties&&(o=s.coordinateProperties.times||s.coordinateProperties.coordTimes);let n=null;if(Array.isArray(o)&&(n=Array.isArray(o[0])?o.reduce((t,e)=>t.concat(e),[]):o.slice()),!n&&e){const t=[];let s=!1;for(const o of e)for(const e of o){const o=e.length>3?e[3]:null;t.push(o),null!=o&&isFinite(o)&&(s=!0)}n=s?t:null}if(!n)return null;let i=0;const l=n.map(t=>{if(null==t||""===t)return null;const e="number"==typeof t?t>1e12?t:1e3*t:Date.parse(t);return isFinite(e)?(i++,e):null});return i>=2?l:null}function b(t,e,s){let o=t;if("function"==typeof o)try{o=o(e,s)}catch(t){return null}if(Array.isArray(o)&&(o=o[0]),o&&o.getStroke){const t=o.getStroke();if(t)return t.getColor()}return null}const v=(t,e)=>{if("imperial"===e){const e=t/1609.344;return e<.2?`${Math.round(3.28084*t)} ft`:`${e.toFixed(e<10?2:1)} mi`}return t<1e3?`${Math.round(t)} m`:`${(t/1e3).toFixed(t<1e4?2:1)} km`},S=(t,e)=>"imperial"===e?`${Math.round(3.28084*t)} ft`:`${Math.round(t)} m`;const E='<svg viewBox="0 0 24 24"><path d="M5 13h14" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round"/></svg>',M='<svg viewBox="0 0 24 24"><path d="M3 19l5-7 4 4 4-6 5 9z" fill="currentColor" opacity=".85"/></svg>',k=h.bisector(t=>t.x).left,w={terrarium:{url:"https://s3.amazonaws.com/elevation-tiles-prod/terrarium/{z}/{x}/{y}.png",encoding:"terrarium",maxZoom:14,attributions:'Elevation: <a href="https://registry.opendata.aws/terrain-tiles/">Terrain Tiles</a> (AWS Open Data)'},ign:{api:"ign",url:"https://data.geopf.fr/altimetrie/1.0/calcul/alti/rest/elevation.json",resource:"ign_rge_alti_wld",batch:200,minInterval:1100,attributions:'Elevation: <a href="https://geoservices.ign.fr/rgealti">RGE ALTI</a> (IGN)'}};function z(t){const e=Math.max(1,t.batch||200),s=t.minInterval||0;return o=>{const n=[];let i=0;const l=r=>{if(r>=o.length)return Promise.resolve(n);const a=o.slice(r,r+e),h=Math.max(0,s-(Date.now()-i));return new Promise(t=>setTimeout(t,h)).then(()=>(i=Date.now(),fetch(function(t,e){const s=t=>t.toFixed(6),o=t.url.indexOf("?")>=0?"&":"?";let n=t.url+o+"resource="+encodeURIComponent(t.resource)+"&delimiter=|&zonly=true&lon="+e.map(t=>s(t[0])).join("|")+"&lat="+e.map(t=>s(t[1])).join("|");return t.apiKey&&(n+="&"+(t.apiKeyParam||"apikey")+"="+encodeURIComponent(t.apiKey)),n}(t,a)))).then(t=>t&&t.ok?t.json():null).then(t=>{const s=t&&t.elevations;if(!Array.isArray(s)||s.length!==a.length)return null;for(const t of s)n.push(null==t||t<=-99999?null:t);return l(r+e)})};return l(0)}}const C={source:"terrarium",zoom:"auto",maxZoom:14,maxTiles:32,concurrency:6,tileSize:256},P={terrarium:(t,e,s)=>256*t+e+s/256-32768,mapbox:(t,e,s)=>.1*(65536*t+256*e+s)-1e4},T=20037508.342789244;function j(t,e){const s=t.indexOf("?")>=0?"&":"?";return t.replace(/[?&]$/,"")+s+Object.keys(e).map(t=>t+"="+encodeURIComponent(e[t])).join("&")}function A(t,e,s,o,n){const i=Object.assign({SERVICE:"WMS",REQUEST:"GetMap",VERSION:"1.3.0",FORMAT:"image/png",TRANSPARENT:"false",STYLES:""},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.WIDTH=n,i.HEIGHT=n,i.BBOX=function(t,e,s){const o=2*T/Math.pow(2,t),n=e*o-T,i=T-s*o;return[n,i-o,n+o,i]}(e,s,o).join(","),j(t.url,i)}function L(t){const e=t.olSource,s=t.band||0;return i=>{const l=e.getTileGrid&&e.getTileGrid();return(l?Promise.resolve(null):Promise.resolve(e.getView?e.getView():null)).then(r=>{const a=l||e.getTileGrid&&e.getTileGrid()||r&&r.tileGrid;if(!a)return null;const h=o.get(r&&r.projection||e.getProjection&&e.getProjection()||"EPSG:3857"),c=a.getResolutions?a.getResolutions().length-1:0,u=e.bandCount||1,p=i.map(t=>o.transform([t[0],t[1]],"EPSG:4326",h)),d=a.getExtent&&a.getExtent()||r&&r.extent||null,m=t=>{const e=a.getResolution(t),s=a.getOrigin(t);let o=a.getTileSize(t);o=Array.isArray(o)?o:[o,o];const n=d?Math.round((d[2]-d[0])/e):1/0,i=d?Math.round((d[3]-d[1])/e):1/0,l=t=>Math.min(n-1,Math.max(0,t)),r=t=>Math.min(i-1,Math.max(0,t)),h=new Map,c=p.map(t=>{const n=(t[0]-s[0])/e-.5,i=(s[1]-t[1])/e-.5,a=l(Math.floor(n)),c=r(Math.floor(i));for(let t=0;t<2;t++)for(let e=0;e<2;e++){const s=Math.floor(l(a+t)/o[0]),n=Math.floor(r(c+e)/o[1]);h.set(s+"/"+n,[s,n])}return{i0:a,j0:c,tx:Math.min(1,Math.max(0,n-a)),ty:Math.min(1,Math.max(0,i-c)),clampI:l,clampJ:r}});return{res:e,origin:s,ts:o,need:h,at:c,clampI:l,clampJ:r}};let f=c,_=m(f);for(;f>0&&_.need.size>t.maxTiles;)f--,_=m(f);if(_.need.size>t.maxTiles)return null;const g=Array.from(_.need.keys());return Promise.all(g.map(t=>{const s=_.need.get(t);return(o=e.getTile(f,s[0],s[1],1,h),new Promise(t=>{const e=()=>{const e=o.getState();return e===n.LOADED?(t(o.getData?o.getData():null),!0):(e===n.ERROR||e===n.EMPTY)&&(t(null),!0)};if(e())return;const s=()=>{e()&&o.removeEventListener("change",s)};o.addEventListener("change",s),o.load&&o.load()})).then(e=>[t,e]);var o})).then(t=>{const e=new Map(t),o=(t,o)=>{const n=Math.floor(_.clampI(t)/_.ts[0]),i=Math.floor(_.clampJ(o)/_.ts[1]);t=_.clampI(t),o=_.clampJ(o);const l=e.get(n+"/"+i);if(!l)return null;const r=t-n*_.ts[0],a=l[((o-i*_.ts[1])*_.ts[0]+r)*u+s];return null!=a&&isFinite(a)?a:null};return _.at.map(t=>{const e=o(t.i0,t.j0),s=o(t.i0+1,t.j0),n=o(t.i0,t.j0+1),i=o(t.i0+1,t.j0+1);if(null==e||null==s||null==n||null==i)return null;const l=e+(s-e)*t.tx;return l+(n+(i-n)*t.tx-l)*t.ty})})})}}function $(t){const e=t.featureInfo,s=Math.max(1,t.concurrency||6);return t=>{const n=new Array(t.length);let i=0,l=!1;const r=()=>{if(l||i>=t.length)return Promise.resolve();const s=i++;return fetch(function(t,e){const s=o.fromLonLat([e[0],e[1]]),n=t.resolution||1,i=Object.assign({SERVICE:"WMS",REQUEST:"GetFeatureInfo",VERSION:"1.3.0",INFO_FORMAT:"application/json",STYLES:"",FEATURE_COUNT:1},t.params||{}),l=0===String(i.VERSION).indexOf("1.1")?"SRS":"CRS";return delete i.SRS,delete i.CRS,i[l]=t.projection||"EPSG:3857",i.LAYERS=t.layers,i.QUERY_LAYERS=t.queryLayers||t.layers,i.WIDTH=1,i.HEIGHT=1,i.I=0,i.J=0,i.X=0,i.Y=0,i.BBOX=[s[0]-n,s[1]-n,s[0]+n,s[1]+n].join(","),j(t.url,i)}(e,t[s])).then(t=>t&&t.ok?t.json():null).then(t=>(n[s]=function(t,e){const s=t&&t.features&&t.features[0],o=s&&s.properties;if(!o)return null;if(e){const t=Number(o[e]);return isFinite(t)?t:null}for(const t of Object.keys(o)){const e=Number(o[t]);if(null!==o[t]&&""!==o[t]&&isFinite(e))return e}return null}(t,e.property),r())).catch(()=>{l=!0})},a=[];for(let e=0;e<Math.min(s,t.length);e++)a.push(r());return Promise.all(a).then(()=>l?null:n)}}class B{constructor(t){this.cfg=t,this.decode="function"==typeof t.encoding?t.encoding:P[t.encoding]||P.terrarium,this.tileUrl=function(t){const e=t.olSource;if(e&&"function"==typeof e.getTileUrlFunction){const t=e.getTileUrlFunction(),s=o.get("EPSG:3857");return(e,o,n)=>t([e,o,n],1,s)}return t.wms?(e,s,o)=>A(t.wms,e,s,o,t.tileSize):(e,s,o)=>t.url.replace("{z}",e).replace("{x}",s).replace("{y}",o)}(t),this.tiles=new Map}_neighbours(t,e,s){const o=function(t,e,s,o){const n=o*Math.pow(2,s),i=Math.sin(e*Math.PI/180);return[(t+180)/360*n,(.5-Math.log((1+i)/(1-i))/(4*Math.PI))*n]}(t,e,s,this.cfg.tileSize),n=o[0]-.5,i=o[1]-.5,l=Math.floor(n),r=Math.floor(i);return{i0:l,j0:r,tx:n-l,ty:i-r}}_key(t,e,s){const o=this.cfg.tileSize,n=o*Math.pow(2,s),i=Math.min(n-1,Math.max(0,e)),l=(t%n+n)%n;return{key:s+"/"+Math.floor(l/o)+"/"+Math.floor(i/o),ii:l,jj:i}}_at(t,e,s){const o=this.cfg.tileSize,n=this._key(t,e,s),i=this.tiles.get(n.key);if(!i)return null;const l=4*(n.jj%o*o+n.ii%o),r=this.decode(i[l],i[l+1],i[l+2],i[l+3]);return null!=r&&isFinite(r)?r:null}sample(t,e,s){const o=this._neighbours(t,e,s),n=this._at(o.i0,o.j0,s),i=this._at(o.i0+1,o.j0,s),l=this._at(o.i0,o.j0+1,s),r=this._at(o.i0+1,o.j0+1,s);if(null==n||null==i||null==l||null==r)return null;const a=n+(i-n)*o.tx;return a+(l+(r-l)*o.tx-a)*o.ty}tilesFor(t,e){const s=new Set;for(const o of t){const t=this._neighbours(o[0],o[1],e);for(let o=0;o<2;o++)for(let n=0;n<2;n++)s.add(this._key(t.i0+o,t.j0+n,e).key)}return s}_fetch(t){const e=t.split("/"),s=this.tileUrl(+e[0],+e[1],+e[2]);return new Promise(t=>{const e=new Image;e.crossOrigin="anonymous",e.onload=()=>{try{const s=this.cfg.tileSize,o=document.createElement("canvas");o.width=s,o.height=s;const n=o.getContext("2d",{willReadFrequently:!0});n.drawImage(e,0,0,s,s),t(n.getImageData(0,0,s,s).data)}catch(e){t(null)}},e.onerror=()=>t(null),e.src=s})}load(t){const e=Array.from(t).filter(t=>!this.tiles.has(t));let s=0,o=!0;const n=()=>{if(s>=e.length)return Promise.resolve();const t=e[s++];return this._fetch(t).then(e=>(this.tiles.set(t,e),e||(o=!1),n()))},i=[];for(let t=0;t<Math.min(this.cfg.concurrency,e.length);t++)i.push(n());return Promise.all(i).then(()=>o)}}class F extends t{constructor(t){const e=f(d,t||{});-1===u.indexOf(e.position)&&(e.position="bottom");const s=e.labels;e.labels=m(e.lang,s);const o=function(t){const e=document.createElement("div");return e.className=`ol-elevation-profile ol-unselectable ol-control oep-pos-${t.position} oep-theme-${"string"==typeof t.theme?t.theme:"custom"}`+("floating"===t.immersion?" oep-floating":""),e}(e);super({element:o,target:t&&t.target}),this.options=e,this._userLabels=s,this.slopeColors=e.slopeColors||null,this._feature=null,this._fullSamples=null,this._fullStats=null,this._samples=null,this._stats=null,this._marker=null,this._collapsed=!!e.collapsed,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._demZ=null,this._demFor=null,this._demSeq=0,this._demLoading=!1,this._trackLines=null,this._linesFor=null,this._onResize=()=>{this._feature&&!this._collapsed&&this._render()},this._buildDom(o),o.style.display="none"}get _cropMode(){return this._crops.length>0}get _cropDepth(){return this._crops.length}get _cropMax(){const t=this.options.zoomLevels;return null==t?3:Math.max(1,0|t)}static featureHasZ(t){const e=t&&t.getGeometry&&t.getGeometry();if(!e)return!1;for(const t of y(e))for(const e of t)if(e.length>2&&isFinite(e[2]))return!0;return!1}static featureHasTime(t){const e=t&&t.getGeometry&&t.getGeometry();return!!e&&!!x(t,y(e))}_buildDom(t){const e=this.options;this._applyTheme(),this._applyTransparency();const s=document.createElement("div");s.className="oep-header",this._titleEl=document.createElement("span"),this._titleEl.className="oep-title",this._titleEl.textContent=e.labels.empty,this._statsEl=document.createElement("span"),this._statsEl.className="oep-stats",s.appendChild(this._titleEl),s.appendChild(this._statsEl),this._toolbar=document.createElement("span"),this._toolbar.className="oep-toolbar";const o=(t,e,s,o)=>{const n=document.createElement("button");return n.type="button",n.className=`oep-tbtn ${t}`,n.innerHTML=e,n.title=s,n.setAttribute("aria-label",s),n.addEventListener("click",o),this._toolbar.appendChild(n),n};this._btnA=o("oep-a",'<svg viewBox="0 0 24 24"><path d="M7 5v14M11 12h8m0 0-3-3m3 3-3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomStart,()=>this._arm("A")),this._btnB=o("oep-b",'<svg viewBox="0 0 24 24"><path d="M17 5v14M13 12H5m0 0 3-3m-3 3 3 3" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomEnd,()=>this._arm("B")),this._btnBack=o("oep-back",'<svg viewBox="0 0 24 24"><path d="M10 6 4 12l6 6M4 12h10a6 6 0 0 1 6 6" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomBack,()=>this._popCrop()),this._btnAll=o("oep-all",'<svg viewBox="0 0 24 24"><path d="M4 12h16M4 12l4-4M4 12l4 4M20 12l-4-4M20 12l-4 4" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.zoomAll,()=>this._exitZoom()),this._btnPng=o("oep-png",'<svg viewBox="0 0 24 24"><path d="M12 4v10m0 0 4-4m-4 4-4-4M5 18h14" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/></svg>',e.labels.exportPng,()=>this.exportPNG()),s.appendChild(this._toolbar);const n=document.createElement("button");n.className="oep-toggle",n.type="button",n.innerHTML=this._collapsed?M:E,n.addEventListener("click",()=>this.toggleCollapsed()),s.appendChild(n),this._toggleBtn=n,this._applyToggleLabel(),this._legendEl=document.createElement("div"),this._legendEl.className="oep-legend",this._legendEl.style.display="none",this._body=document.createElement("div"),this._body.className="oep-body",t.appendChild(s),t.appendChild(this._legendEl),t.appendChild(this._body),this._applyCollapsable(),this._updateZoomButtons(),this._collapsed&&t.classList.add("oep-collapsed")}_applyLabels(){const t=this.options.labels,e=(t,e)=>{t&&e&&(t.title=e,t.setAttribute("aria-label",e))};e(this._btnA,t.zoomStart),e(this._btnB,t.zoomEnd),e(this._btnBack,t.zoomBack),e(this._btnAll,t.zoomAll),e(this._btnPng,t.exportPng),this._applyToggleLabel(),this._titleEl&&!this._feature&&(this._titleEl.textContent=t.empty)}_applyToggleLabel(){const t=this.options.labels,e=this._collapsed?t.expand:t.collapse;this._toggleBtn&&e&&(this._toggleBtn.title=e,this._toggleBtn.setAttribute("aria-label",e))}_resolveColor(){const t=this.options;return t.color?"auto"===t.color?this._featureColor():t.color:null}_featureColor(){const t=this._feature;if(!t)return null;const e=this.getMap()?this.getMap().getView().getResolution():1;let s=b(t.getStyle&&t.getStyle(),t,e);return!s&&this.options.trackLayer&&(s=b(this.options.trackLayer.getStyle&&this.options.trackLayer.getStyle(),t,e)),function(t){if(null==t)return null;if("string"==typeof t)return t;if(Array.isArray(t)){const e=t.length>3?t[3]:1;return`rgba(${0|t[0]},${0|t[1]},${0|t[2]},${e})`}return null}(s)}_applyTheme(){const t=this.options,e="object"==typeof t.theme?t.theme:c[t.theme]||c.steelblue;this.themeColors=e;const s=this.element,o=this._resolveColor(),n=o||e.area;let i=e.line;if(o)try{i=String(h.color(o).darker(.7))}catch(t){i=o}s.style.setProperty("--oep-area",n),s.style.setProperty("--oep-line",i),s.style.setProperty("--oep-axis",e.axis),s.style.setProperty("--oep-text",e.text),s.style.setProperty("--oep-focus",e.focus)}_applyTransparency(){const t=this.options.transparency;let e;e=!1===t||null==t?1:!0===t?this.options.transparencyLevel:Math.max(0,Math.min(1,+t)),this.element.style.setProperty("--oep-bg",`rgba(255,255,255,${e})`),this.element.classList.toggle("oep-transparent",e<1)}_applyCollapsable(){const t=this.options.collapsable;this._toggleBtn.style.display=t?"":"none",!t&&this._collapsed&&this.toggleCollapsed(!1)}toggleCollapsed(t){this._collapsed="boolean"==typeof t?t:!this._collapsed,this.element.classList.toggle("oep-collapsed",this._collapsed),this._toggleBtn.innerHTML=this._collapsed?M:E,this._applyToggleLabel(),!this._collapsed&&this._feature&&this._render(),this._adjustAttribution()}_availWidth(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement();return e&&e.clientWidth||("undefined"!=typeof window?window.innerWidth:1024)}_isMobile(){return this.options.responsive&&"undefined"!=typeof window&&window.innerWidth<=(this.options.mobileBreakpoint||640)}_applyPlacement(){const t=this._isMobile();let e=this.options.position;return t&&(e=/top/.test(e)?"top":"bottom"),this.element.className=this.element.className.replace(/oep-pos-\S+/,`oep-pos-${e}`),this.element.classList.toggle("oep-mobile",t),t}_adjustAttribution(){const t=this.getMap(),e=t&&t.getTargetElement&&t.getTargetElement(),s=e&&e.querySelector&&e.querySelector(".ol-attribution");if(!s)return;if(s.style.bottom="",s.style.right="","none"===this.element.style.display||this._collapsed)return;const o=e.getBoundingClientRect(),n=this.element.getBoundingClientRect();if(!n.height)return;const i=o.bottom-n.bottom,l=o.right-n.right;i<n.height&&l<24&&(s.style.right=`${Math.max(0,Math.round(l))}px`,s.style.bottom=`${Math.round(n.height+2*i)}px`)}setMap(t){const o=this.getMap();if(super.setMap(t),this._mapKeys&&(this._mapKeys.forEach(s.unByKey),this._mapKeys=null),o&&"undefined"!=typeof window&&window.removeEventListener("resize",this._onResize),this._marker&&!t&&this._marker.setPosition(void 0),!t)return;const n=this.options;if(n.dataProjection||(n.dataProjection=t.getView().getProjection()),n.marker&&!this._marker){const s=document.createElement("div");s.className="oep-marker",this._marker=new e({element:s,positioning:"center-center",stopEvent:!1}),t.addOverlay(this._marker)}"undefined"!=typeof window&&window.addEventListener("resize",this._onResize);const i=e=>t.forEachFeatureAtPixel(e,t=>{const e=t.getGeometry();return(s=e)&&/^(Multi)?(LineString|Polygon)$|^LinearRing$/.test(s.getType())?t:void 0;var s});this._mapKeys=[],this._mapKeys.push(t.on("click",t=>{const e=i(t.pixel);"mouseover"!==this.options.show&&e&&e!==this._feature&&this.setFeature(e),this.options.hideOnMapClick&&!e&&this._feature&&this.clear()})),this._mapKeys.push(t.on("pointermove",e=>{if("mouseover"===this.options.show){const t=i(e.pixel);t&&t!==this._feature&&this.setFeature(t)}if(!this.options.followMap||!this._feature||this._collapsed)return;const s=this._closestOnProfile(e.coordinate);if(!s)return;const o=t.getPixelFromCoordinate(s);o&&(Math.hypot(o[0]-e.pixel[0],o[1]-e.pixel[1])<14?this._focusByCoord(s):this._clearFocus())})),this._mapKeys.push(t.on("moveend",()=>{const e=this._crops[this._crops.length-1];e&&e.fitRes&&t.getView().getResolution()>1.25*e.fitRes&&this._popCrop()})),this._mapKeys.push(t.on("change:size",this._onResize))}setFeature(t){return this._feature=t||null,this._crops=[],this._off=0,this._zoomA=null,this._zoomB=null,this._armed=null,t?(this.element.style.display="",this._compute(),this._fillFromDem(t),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render(),this):(this._fullSamples=this._samples=null,this._demZ=this._demFor=null,this._trackLines=this._linesFor=null,this._clear(),this)}clear(){return this.setFeature(null)}getStats(){return this._stats}setTheme(t){return this.options.theme=t,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setColor(t){return this.options.color=t||null,this._applyTheme(),this._feature&&!this._collapsed&&this._render(),this}setOptions(t){return this.options=f(this.options,t||{}),t&&"slopeColors"in t&&(this.slopeColors=t.slopeColors||null),t&&(t.theme||"color"in t)&&this._applyTheme(),t&&("transparency"in t||"transparencyLevel"in t)&&this._applyTransparency(),t&&"collapsable"in t&&this._applyCollapsable(),t&&"labels"in t&&(this._userLabels=f(this._userLabels||{},t.labels)),t&&("lang"in t||"labels"in t)&&(this.options.labels=m(this.options.lang,this._userLabels),this._applyLabels()),t&&("zoom"in t||"exportPng"in t)&&this._updateZoomButtons(),t&&void 0!==t.width&&"number"==typeof t.width&&(this.options.width=t.width),t&&"dem"in t&&(this._demZ=null,this._demFor=null,this._trackLines=null,this._linesFor=null),this._feature&&(this._compute(),this._fillFromDem(this._feature),this._updateZoomButtons(),this._collapsed?this._renderTitle():this._render()),this}_fillFromDem(t){const e=function(t){if(!t)return null;if("function"==typeof t)return Object.assign({},C,{sample:t});const e=!0===t||"string"==typeof t?{source:!0===t?"terrarium":t}:Object.assign({},t);if("function"==typeof e.sample)return Object.assign({},C,e);if(e.track){const t=Object.assign({},C,e);return t.track=Object.assign({coords:"coords",parse:null,fetchOptions:null},"string"==typeof e.track?{url:e.track}:e.track),t.track.url?t:null}if(e.featureInfo){const t=Object.assign({},C,e);return t.sample=$(t),t}if(e.olSource&&"function"!=typeof e.olSource.getTileUrlFunction&&"function"==typeof e.olSource.getTile){const t=Object.assign({},C,e);return t.sample=L(t),t}const s=e.url||e.wms||e.olSource,o=w[e.source]||(s?{}:w.terrarium),n=Object.assign({},C,o,e);return"ign"===n.api?(n.sample=z(n),n):n.url||n.wms||n.olSource?n:null}(this.options.dem);if(!e||!t||this._demFor===t||this._linesFor===t)return;if(F.featureHasZ(t))return;if(!e.sample&&("undefined"==typeof Image||"undefined"==typeof document))return;const s=t.getGeometry&&t.getGeometry(),n=s?y(s):[],i=this.options.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",l=[];for(const t of n)for(const e of t)l.push(o.toLonLat(e,i));if(!l.length&&!e.track)return;const r=++this._demSeq;this._demLoading=!0;try{this._startFill(e,r,t,l,i)}catch(e){this._demDone(r,t,null,l.length,null,0)}}_startFill(t,e,s,o,n){if(t.track)return void this._startTrackFill(t,e,s,o.length,n);if(t.sample)return void Promise.resolve().then(()=>t.sample(o,{feature:s,projection:n})).then(t=>this._demDone(e,s,t,o.length,null,0)).catch(()=>this._demDone(e,s,null,o.length,null,0));const i=new B(t),l=function(t,e,s){if("number"==typeof s.zoom)return s.zoom;for(let o=s.maxZoom;o>0;o--)if(t.tilesFor(e,o).size<=s.maxTiles)return o;return 1}(i,o,t);i.load(i.tilesFor(o,l)).then(t=>{const n=t?o.map(t=>i.sample(t[0],t[1],l)):null;this._demDone(e,s,n,o.length,l,i.tiles.size)}).catch(()=>this._demDone(e,s,null,o.length,l,0))}_startTrackFill(t,e,s,o,n){const i=function(t,e){if("function"==typeof t)return t(e)||null;if("string"!=typeof t||!e)return null;let s=!0;const o=t.replace(/\{(\w+)\}/g,(t,o)=>{const n=e.get(o);return null==n||""===n?(s=!1,""):encodeURIComponent(String(n))});return s?o:null}(t.track.url,s);i?Promise.resolve().then(()=>fetch(i,t.track.fetchOptions||void 0)).then(t=>{if(!t.ok)throw new Error(String(t.status));return t.json()}).then(i=>{const l=t.track.parse?t.track.parse(i,s):Array.isArray(i)?i:i&&i[t.track.coords];this._trackDone(e,s,l,o,n)}).catch(()=>this._demDone(e,s,null,o,null,0)):this._demDone(e,s,null,o,null,0)}_trackDone(t,e,s,n,i){const l=()=>this._demDone(t,e,null,n,null,0);if(!Array.isArray(s)||!s.length)return l();if("number"==typeof s[0])return void this._demDone(t,e,s,n,null,0);if(t!==this._demSeq||this._feature!==e)return;const r=t=>null!=t&&isFinite(t),a=[];for(const t of s){if(!t||t.length<3||!r(t[0])||!r(t[1])||!r(t[2]))return l();const e=o.transform([t[0],t[1]],"EPSG:4326",i);a.push([e[0],e[1],t[2]])}if(a.length<2)return l();this._demLoading=!1,this._trackLines=[a],this._linesFor=e,this._demZ=null,this._demFor=null,this._compute(),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:!0,zoom:null,tiles:0})}_demDone(t,e,s,o,n,i){if(t!==this._demSeq||this._feature!==e)return;const l=Array.isArray(s)&&s.length===o&&s.every(t=>null!=t&&isFinite(t));this._demLoading=!1,l&&(this._demZ=s,this._demFor=e,this._compute()),this._updateZoomButtons(),this._collapsed||this._render(),this.dispatchEvent({type:"demload",ok:l,zoom:n,tiles:i})}_compute(){const t=this.options,e=this._linesFor===this._feature&&this._trackLines,s=this._feature.getGeometry&&this._feature.getGeometry(),n=e?this._trackLines:s?y(s):[],l=t.dataProjection||this.getMap()&&this.getMap().getView().getProjection()||"EPSG:3857",r=this._demFor===this._feature?this._demZ:null,a=e?null:x(this._feature,n);this._hasTime=!!a;const h=!1!==t.ignoreStops,c=null!=t.stopSpeed?t.stopSpeed:.5,u=[];let p=0,d=null,m=-1,f=0,_=null;for(const t of n)for(const e of t){m++;const t=o.toLonLat(e,l);let s=0;d&&(s=i.getDistance(d,t),p+=s);let n=null;if(a&&null!=a[m]){const t=a[m];if(null!=_){const e=(t-_)/1e3;e>0&&(!h||s/e>=c)&&(f+=e)}n=f,_=t}d=t;const g=e.length>2&&isFinite(e[2])?e[2]:r?r[m]:0;u.push({x:p,z:g,coord:e,t:n})}t.smoothing>0&&this._smooth(u,t.smoothing);const g=this._decimate(u,t.maxPoints);this._addSlope(g),this._fullSamples=g,this._fullStats=this._statsOf(g,!0),this._applyCrops()}_pxPerCm(){try{const t=document.createElement("div");t.style.cssText="position:absolute;left:-9999px;top:0;width:1cm;height:1cm",(this.element||document.body).appendChild(t);const e=t.getBoundingClientRect().height;if(t.remove(),e>0)return e}catch(t){}return 96/2.54}_yScale(t,e,s,o){const n=t.min-e,i=t.max+e,l=s/this._pxPerCm(),r=o/this._pxPerCm(),a=e=>r>0&&e>0?t.distance/r/(e/l):null;let c=this._verticalScaleFor(t,o);if(!(c>0)){const e=h.scaleLinear().domain([n,i]).range([s,0]).nice(),o=e.domain(),l=a(o[1]-o[0]),u=this._plafondExageration();if(!(u>0)||null==l||l<=u)return this._vScale=null,this._vExaggeration=l,e;c=t.distance/r/u}const u=Math.max(c*l,i-n);this._vScale=u/l,this._vExaggeration=a(u);const p=Math.min(0,n);let d=(n+i)/2-u/2;return d<p&&(d=p),h.scaleLinear().domain([d,d+u]).range([s,0])}_plafondExageration(){const t=this.options.verticalScale,e=t&&"object"==typeof t?Number(t.maxExaggeration):0;return e>0?e:0}_verticalScaleFor(t,e){const s=this.options.verticalScale;if("number"==typeof s)return s;const o=s&&"object"==typeof s?Number(s.exaggeration):0;if(!(o>0&&t.distance>0&&e>0))return 0;const n=e/this._pxPerCm();return t.distance/n/o}_statsOf(t,e){let s=0,o=0,n=1/0,i=-1/0,l=0;for(let e=0;e<t.length;e++){const r=t[e].z;if(r<n&&(n=r),r>i&&(i=r),e>0){const n=r-t[e-1].z;n>0?s+=n:o-=n}const a=Math.abs(t[e].slope||0);a>l&&(l=a)}const r=t.length?t[t.length-1].x-t[0].x:0,a=t.length?t[0].t:null,h=t.length?t[t.length-1].t:null;return{distance:r,duration:null!=a&&null!=h?h-a:null,ascent:s,descent:o,min:isFinite(n)?n:0,max:isFinite(i)?i:0,maxAbsSlope:l,points:t.length}}_smooth(t,e){if(!(e>0)||t.length<3)return;const s=e/2,o=t.map(t=>t.z);let n=0,i=0,l=0;for(let e=0;e<t.length;e++){const r=t[e].x;for(;n<t.length&&t[n].x<r-s;)l-=o[n],n++;for(;i<t.length&&t[i].x<=r+s;)l+=o[i],i++;t[e].z=i>n?l/(i-n):o[e]}}_decimate(t,e){const s=t=>({x:t.x,z:t.z,coord:t.coord,t:t.t});if(!e||t.length<=e)return t.map(s);const o=t.length/e,n=[];for(let i=0;i<e;i++)n.push(s(t[Math.floor(i*o)]));return n.push(s(t[t.length-1])),n}_addSlope(t){for(let e=1;e<t.length;e++){const s=t[e].x-t[e-1].x;t[e].slope=s>0?(t[e].z-t[e-1].z)/s*100:0}t.length&&(t[0].slope=t.length>1?t[1].slope:0)}_slopeScale(){const t=this.options.slopeClassSize||2.5,e=this.options.maxClasses||8,s=Math.max(1,Math.floor((this._stats.maxAbsSlope||0)/t)),o=Math.min(s,e-1),n=s>o;let i;if(this.slopeColors&&this.slopeColors.length){const t=h.interpolateRgbBasis(this.slopeColors);i=e=>t(o?e/o:0)}else{const t=h.scaleLinear().domain([0,.16,.42,.68,1]).range(["#2166ac","#27a35a","#ffe000","#f4791f","#d7191c"]).interpolate(h.interpolateRgb).clamp(!0);i=e=>String(t(o?e/o:0))}return{classSize:t,maxIdx:o,capped:n,colorByIndex:i}}_classIndex(t,e){return Math.min(e.maxIdx,Math.floor(Math.abs(t)/e.classSize))}_fmtDuration(t){if(null==t||!isFinite(t))return"";const e=this.options.labels&&this.options.labels.durationUnits||p.en.durationUnits;if((t=Math.max(0,Math.round(t)))<60)return t+" "+e.s;if(t<3600)return Math.round(t/60)+" "+e.m;if(t<86400){let s=Math.floor(t/3600),o=Math.round(t%3600/60);return 60===o&&(s++,o=0),o?`${s} ${e.h} ${o} ${e.m}`:`${s} ${e.h}`}let s=Math.floor(t/86400),o=Math.round(t%86400/3600);return 24===o&&(s++,o=0),o?`${s} ${e.d} ${o} ${e.h}`:`${s} ${e.d}`}_hasElevation(){const t=this._feature;return!!t&&(!!F.featureHasZ(t)||(!(this._demFor!==t||!this._demZ)||!(this._linesFor!==t||!this._trackLines)))}_renderNoElevation(){if(!this.options.showWithoutElevation)return void(this.element.style.display="none");this.element.style.display="",this._applyTheme(),this._applyPlacement(),this._renderHeader(!0);const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-noelev",e.style.height=`${t}px`,e.setAttribute("role","status"),e.textContent=this.options.labels.noElevation,this._body.appendChild(e),this._clearFocus()}_pickProperty(t,e,s){if(!e||!t||!t.get)return null;for(const o of Array.isArray(e)?e:[e]){const e=t.get(o);if(null!=e&&""!==e&&(!s||s(e)))return e}return null}_renderTitle(){const t=this.options,e=this._feature;if(!e)return;const s=this._pickProperty(e,t.titleProperty)||t.labels.untitled,o=this._pickProperty(e,t.titleLink,g);g(o)?this._titleEl.innerHTML=`<a href="${_(o)}" target="_blank" rel="noopener">${_(s)}</a>`:this._titleEl.textContent=s,this._titleEl.setAttribute("title",s)}_renderHeader(t){const e=this.options,s=this._stats,o=this._feature;if(this._renderTitle(),this._demLoading)return this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._legendEl.innerHTML="",void(this._legendEl.style.display="none");const n=[],i=[];if(e.headerItems.forEach(l=>{if("string"==typeof l){if(t&&("ascent"===l||"descent"===l||"min"===l||"max"===l||"minmax"===l))return;if("distance"===l){if(!(s&&s.distance>0))return;n.push(`<b>${v(s.distance,e.units)}</b>`),i.push(v(s.distance,e.units))}else if("ascent"===l)n.push(`<span class="oep-up">${e.labels.ascent} ${S(s.ascent,e.units)}</span>`),i.push(`${e.labels.ascent} ${S(s.ascent,e.units)}`);else if("descent"===l)n.push(`<span class="oep-down">${e.labels.descent} ${S(s.descent,e.units)}</span>`),i.push(`${e.labels.descent} ${S(s.descent,e.units)}`);else if("min"===l)n.push(S(s.min,e.units)),i.push(S(s.min,e.units));else if("max"===l)n.push(S(s.max,e.units)),i.push(S(s.max,e.units));else if("minmax"===l){const t=`${S(s.min,e.units)}-${S(s.max,e.units)}`;n.push(t),i.push(t)}else if("duration"===l&&null!=s.duration){const t=this._fmtDuration(s.duration);n.push(`<span class="oep-time">${_(e.labels.duration)} ${t}</span>`),i.push(`${e.labels.duration} ${t}`)}}else if(l&&l.property){const t=o.get&&o.get(l.property);if(null==t||""===t)return;const e=l.label?`${l.label} `:"";l.asLink&&g(t)?(n.push(`${e}<a href="${_(t)}" target="_blank" rel="noopener">${_(l.linkText||l.label||t)}</a>`),i.push(`${l.label||""} ${t}`)):(n.push(_(e+t)),i.push(e+t))}}),this._statsEl.innerHTML=n.join(" · "),this._statsEl.setAttribute("title",i.join(" · ")),this._legendEl.innerHTML="",e.slope&&e.slopeLegend&&!t){const t=this._slopeScale();for(let e=0;e<=t.maxIdx;e++){const s=t.colorByIndex(e),o=t.capped&&e===t.maxIdx?`≥ ${e*t.classSize} %`:`${e*t.classSize}-${(e+1)*t.classSize} %`,n=document.createElement("span");n.className="oep-leg-it",n.innerHTML=`<i class="oep-sw" style="background:${s}"></i>${o}`,this._legendEl.appendChild(n)}this._legendEl.style.display=""}else this._legendEl.style.display="none"}_renderSpinner(){const t="number"==typeof this.options.height?this.options.height:180;this._body.innerHTML="";const e=document.createElement("div");e.className="oep-loading",e.style.height=`${t}px`,e.setAttribute("role","status"),e.setAttribute("aria-label",this.options.labels.loading);const s=document.createElement("div");s.className="oep-spinner",e.appendChild(s),this._body.appendChild(e)}_render(){const t=this.options,e=this._stats,s=this._samples;if(!this._demLoading&&!this._hasElevation())return void this._renderNoElevation();if(!s||!s.length)return;this._applyTheme();const o=this._applyPlacement();if(this._renderHeader(),this._demLoading)return void this._renderSpinner();const n=t.margins,i=n.unit||"px",l=t=>"px"===i?t:t*(parseFloat(getComputedStyle(this.element).fontSize)||16),r=this._availWidth(),a="auto"===t.width||"100%"===t.width||"full"===t.width?r:Math.min("number"==typeof t.width?t.width:parseFloat(t.width)||r,r);this.element.style.width=o?"":`${a}px`;const c=this.element.clientWidth||(o?r:a),u=Math.max(220,c-16),p="number"==typeof t.height?t.height:180,d=l(n.top),m=l(n.right),f=l(n.bottom),_=l(n.left),g=Math.max(10,u-_-m),y=Math.max(10,p-d-f),x=null!=t.xTicks?t.xTicks:Math.max(2,Math.round(g/80)),b=null!=t.yTicks?t.yTicks:Math.max(2,Math.round(y/40));this._body.innerHTML="";const v=h.select(this._body).append("svg").attr("class","oep-svg").attr("width",u).attr("height",p).attr("viewBox",`0 0 ${u} ${p}`),S=v.append("g").attr("transform",`translate(${_},${d})`),E=h.scaleLinear().domain([0,e.distance]).range([0,g]),M=.1*(e.max-e.min)||10,k=this._yScale(e,M,y,g);this._x=E,this._y=k,this._dims={innerW:g,innerH:y},t.grid&&S.append("g").attr("class","oep-grid").call(h.axisLeft(k).ticks(b).tickSize(-g).tickFormat(""));const w="imperial"===t.units?1609.344:1e3;const z=h.area().x(t=>E(t.x)).y0(y).y1(t=>k(t.z));if(t.slope){const e=this._slopeScale(),o=[];let n=1;for(;n<s.length;){const t=this._classIndex(s[n].slope,e);let i=n;for(;i+1<s.length&&this._classIndex(s[i+1].slope,e)===t;)i++;S.append("path").datum(s.slice(n-1,i+1)).attr("class","oep-area-slope").attr("fill",e.colorByIndex(t)).attr("d",z),n>1&&o.push(s[n-1]),n=i+1}t.slopeSeparators&&o.forEach(t=>{S.append("line").attr("class","oep-slope-sep").attr("x1",E(t.x)).attr("x2",E(t.x)).attr("y1",k(t.z)).attr("y2",y)})}else S.append("path").datum(s).attr("class","oep-area").attr("d",z);S.append("path").datum(s).attr("class","oep-line").attr("d",h.line().x(t=>E(t.x)).y(t=>k(t.z))),S.append("g").attr("class","oep-axis oep-axis-x").attr("transform",`translate(0,${y})`).call(h.axisBottom(E).ticks(x).tickFormat(t=>(t/w).toFixed(t/w<10?1:0))),S.append("text").attr("class","oep-axis-label").attr("x",g).attr("y",y+f-4).attr("text-anchor","end").text((t=>"imperial"===t?"mi":"km")(t.units)),S.append("g").attr("class","oep-axis oep-axis-y").call(h.axisLeft(k).ticks(b).tickFormat(e=>"imperial"===t.units?Math.round(3.28084*e):e)),t.zoom&&this._cropDepth<this._cropMax&&[["A",this._zoomA],["B",this._zoomB]].forEach(([t,e])=>{if(null==e)return;const s=E(e);S.append("line").attr("class","oep-ab-line").attr("x1",s).attr("x2",s).attr("y1",0).attr("y2",y),S.append("text").attr("class","oep-ab-label").attr("x",s).attr("y",-6).attr("text-anchor","middle").text(t)});const C=S.append("g").attr("class","oep-focus").style("display","none");C.append("line").attr("class","oep-focus-line").attr("y1",0).attr("y2",y),C.append("circle").attr("class","oep-focus-dot").attr("r",4);const P=C.append("g").attr("class","oep-focus-label");P.append("rect").attr("class","oep-focus-bg"),P.append("text").attr("class","oep-focus-txt"),this._focus=C;const T=t=>{const s=h.pointer(t,S.node())[0];return Math.max(0,Math.min(e.distance,E.invert(s)))},j=v.append("rect").attr("class","oep-overlay").attr("x",_).attr("y",d).attr("width",g).attr("height",y);j.on("mousemove",t=>{const e=this._sampleAt(T(t));e&&(this._setFocus(e),this._marker&&this._marker.setPosition(e.coord))}).on("mouseout",()=>this._clearFocus()),j.on("click",t=>this._placeBound(T(t))),this._armed&&j.style("cursor","col-resize"),this._adjustAttribution()}static get _EXPORT_PROPS(){return["fill","fill-opacity","stroke","stroke-width","stroke-dasharray","stroke-linecap","stroke-linejoin","opacity","font-family","font-size","font-weight","text-anchor","shape-rendering"]}_freezeStyles(t,e){const s=F._EXPORT_PROPS,o=getComputedStyle(t);let n="";for(const t of s){const e=o.getPropertyValue(t);e&&(n+=`${t}:${e};`)}e.setAttribute("style",n);const i=t.children,l=e.children;for(let t=0;t<i.length&&t<l.length;t++)this._freezeStyles(i[t],l[t])}_exportSvg(){const t=this._body.querySelector("svg");if(!t)return null;const e=getComputedStyle(this.element),s=e.getPropertyValue("--oep-bg").trim()||"#fff",o=e.getPropertyValue("--oep-text").trim()||"#222",n=e.fontFamily||"system-ui, sans-serif",i=+t.getAttribute("width"),l=+t.getAttribute("height"),r=this._statsEl.textContent?15:0,a="none"!==this._legendEl.style.display?this._legendEl:null,h=28+r+(a?18:0),c=t.cloneNode(!0);c.querySelectorAll(".oep-focus, .oep-overlay").forEach(t=>t.remove()),this._freezeStyles(t,c);const u=t=>_(String(t)),p=[];if(p.push(`<rect width="${i+16}" height="${l+h+8}" fill="${u(s)}"/>`),p.push(`<text x="8" y="21" style="font-family:${u(n)};font-size:13px;font-weight:600;fill:${u(o)}">${u(this._titleEl.textContent)}</text>`),r&&p.push(`<text x="8" y="38" style="font-family:${u(n)};font-size:11px;fill:${u(o)};opacity:.85">${u(this._statsEl.textContent)}</text>`),a){let t=8;const e=28+r+12;for(const s of a.querySelectorAll(".oep-leg-it")){const i=s.querySelector(".oep-sw"),l=i?getComputedStyle(i).backgroundColor:"none",r=s.textContent.trim();p.push(`<rect x="${t}" y="${e-8}" width="10" height="10" fill="${u(l)}"/>`),p.push(`<text x="${t+14}" y="${e}" style="font-family:${u(n)};font-size:10px;fill:${u(o)}">${u(r)}</text>`),t+=14+5.6*r.length+10}}return p.push(`<g transform="translate(8,${h})">${(new XMLSerializer).serializeToString(c)}</g>`),{width:i+16,height:l+h+8,svg:`<svg xmlns="http://www.w3.org/2000/svg" width="${i+16}" height="${l+h+8}" viewBox="0 0 ${i+16} ${l+h+8}">${p.join("")}</svg>`}}exportPNG(t){const e=t||{},s=this._exportSvg();if(!s)return Promise.reject(new Error("ol-elevation-profile: nothing to export"));const o=e.scale||"undefined"!=typeof window&&window.devicePixelRatio||1;return new Promise((t,n)=>{const i=new Image;i.onload=()=>{try{const l=document.createElement("canvas");l.width=Math.round(s.width*o),l.height=Math.round(s.height*o);const r=l.getContext("2d");r.scale(o,o),r.drawImage(i,0,0),l.toBlob(s=>{s?(!1!==e.download&&this._save(s,e.filename),t(s)):n(new Error("ol-elevation-profile: PNG encoding failed"))},"image/png")}catch(t){n(t)}},i.onerror=()=>n(new Error("ol-elevation-profile: SVG could not be rasterised")),i.src="data:image/svg+xml;charset=utf-8,"+encodeURIComponent(s.svg)})}_save(t,e){const s=e||`${(this._titleEl.textContent||"profile").replace(/[\\/:*?"<>|]+/g,"-").trim()}.png`,o=URL.createObjectURL(t),n=document.createElement("a");n.href=o,n.download=s,document.body.appendChild(n),n.click(),n.remove(),setTimeout(()=>URL.revokeObjectURL(o),1e3)}_arm(t){this._armed=this._armed===t?null:t,this._updateZoomButtons(),this._focus&&this._render()}_placeBound(t){if(!this._armed||this._cropDepth>=this._cropMax)return;const e="A"===this._armed?"B":"A";"A"===this._armed?this._zoomA=t:this._zoomB=t;const s=null!=this._zoomA&&null!=this._zoomB;this._armed=s?null:e,this._updateZoomButtons(),s?this._pushCrop(this._zoomA,this._zoomB):this._render()}_updateZoomButtons(){const t=this.options,e=!!this._feature,s=!!t.zoom&&e,o=!!t.exportPng&&e;this._toolbar.style.display=s||o?"":"none",this._btnPng.style.display=o?"":"none";const n=this._cropDepth,i=n<this._cropMax;this._btnA.style.display=s&&i?"":"none",this._btnB.style.display=s&&i?"":"none",this._btnBack.style.display=s&&n>1?"":"none",this._btnAll.style.display=s&&n>0?"":"none",this._btnA.classList.toggle("armed","A"===this._armed),this._btnB.classList.toggle("armed","B"===this._armed)}_applyCrops(){if(!this._crops.length)return this._off=0,this._samples=this._fullSamples,this._stats=this._fullStats,null;const{a:t,b:e}=this._crops[this._crops.length-1],s=this._fullSamples.filter(s=>s.x>=t&&s.x<=e);if(s.length<2)return this._crops.pop(),this._applyCrops();const o=s[0].x,n=null!=s[0].t?s[0].t:0;return this._off=o,this._samples=s.map(t=>({x:t.x-o,z:t.z,coord:t.coord,slope:t.slope,t:null!=t.t?t.t-n:null})),this._stats=this._statsOf(this._samples,!1),s.map(t=>t.coord)}_fitMap(t){const e=this.getMap();if(!e)return null;let s=null;if(t&&t.length?s=l.boundingExtent(t):this._feature&&(s=this._feature.getGeometry().getExtent()),!s)return null;const o=e.getView();let n=null;try{n=o.getResolutionForExtent(s,e.getSize())}catch(t){n=null}return o.fit(s,{padding:[40,40,40,40],duration:400}),n}_pushCrop(t,e){if(this._zoomA=null,this._zoomB=null,this._armed=null,this._cropDepth>=this._cropMax)return this._updateZoomButtons(),void this._render();const s=this._off+Math.min(t,e),o=this._off+Math.max(t,e);let n=0;for(let t=0;t<this._fullSamples.length;t++){const e=this._fullSamples[t].x;e>=s&&e<=o&&n++}if(n<2)return this._updateZoomButtons(),void this._render();this._crops.push({a:s,b:o,fitRes:null});const i=this._applyCrops();this._updateZoomButtons(),this._render();const l=this._crops[this._crops.length-1];l&&(l.fitRes=this._fitMap(i))}_applyZoom(){null!=this._zoomA&&null!=this._zoomB&&this._pushCrop(this._zoomA,this._zoomB)}_popCrop(){if(!this._crops.length)return;this._crops.pop(),this._zoomA=null,this._zoomB=null,this._armed=null;const t=this._applyCrops();this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(t)}_exitZoom(){this._crops.length=0,this._zoomA=null,this._zoomB=null,this._armed=null,this._applyCrops(),this._updateZoomButtons(),this._collapsed||this._render(),this._fitMap(null)}_closestOnProfile(t){const e=this._feature&&this._feature.getGeometry();if(!e)return null;if(!/Polygon/.test(e.getType()))return e.getClosestPoint(t);const s=this._projectOn(this._fullSamples,t);return s?s.coord:null}_projectOn(t,e){if(!t||!t.length)return null;if(1===t.length)return{x:t[0].x,coord:t[0].coord.slice(0,2)};let s=null,o=1/0;for(let n=1;n<t.length;n++){const i=t[n-1].coord,l=t[n].coord,r=l[0]-i[0],a=l[1]-i[1],h=r*r+a*a;let c=h>0?((e[0]-i[0])*r+(e[1]-i[1])*a)/h:0;c=c<0?0:c>1?1:c;const u=i[0]+r*c,p=i[1]+a*c,d=u-e[0],m=p-e[1],f=d*d+m*m;f<o&&(o=f,s={x:t[n-1].x+(t[n].x-t[n-1].x)*c,coord:[u,p]})}return s}_tooltipText(t){const e=this.options,s=[];return e.tooltipItems.forEach(o=>{var n;"distance"===o?s.push(v(t.x,e.units)):"elevation"===o?s.push(S(t.z,e.units)):"slope"===o?s.push(`${(n=t.slope||0)>=0?"+":""}${n.toFixed(1)} %`):"time"===o&&null!=t.t&&s.push(this._fmtDuration(t.t))}),s.join(" · ")}_setFocus(t){if(!this._focus)return;const e=this._x,s=this._y;this._focus.style("display",null),this._focus.select(".oep-focus-line").attr("x1",e(t.x)).attr("x2",e(t.x)),this._focus.select(".oep-focus-dot").attr("cx",e(t.x)).attr("cy",s(t.z));let o=s(t.z)-16;o<12&&(o=s(t.z)+22);const n=this._focus.select(".oep-focus-txt").attr("x",e(t.x)).attr("y",o).text(this._tooltipText(t)),i=n.node().getBBox();this._focus.select(".oep-focus-bg").attr("x",i.x-4).attr("y",i.y-2).attr("width",i.width+8).attr("height",i.height+4),e(t.x)+i.width/2>this._dims.innerW?n.attr("text-anchor","end"):e(t.x)-i.width/2<0?n.attr("text-anchor","start"):n.attr("text-anchor","middle")}_sampleAt(t){const e=this._samples;if(!e||!e.length)return null;if(1===e.length)return e[0];const s=e[0].x,o=e[e.length-1].x,n=Math.max(s,Math.min(o,t)),i=Math.min(Math.max(k(e,n,1),1),e.length-1),l=e[i-1],r=e[i],a=r.x-l.x,h=a>0?(n-l.x)/a:0,c=(t,e)=>t+(e-t)*h;return{x:n,z:c(l.z,r.z),coord:[c(l.coord[0],r.coord[0]),c(l.coord[1],r.coord[1])],slope:r.slope,t:null!=l.t&&null!=r.t?c(l.t,r.t):null}}_focusByCoord(t){const e=this._projectOn(this._samples,t);if(!e)return;const s=this._sampleAt(e.x);s&&(this._setFocus(s),this._marker&&this._marker.setPosition(s.coord))}_clearFocus(){this._focus&&this._focus.style("display","none"),this._marker&&this._marker.setPosition(void 0)}_clear(){this._body.innerHTML="",this._legendEl.innerHTML="",this._legendEl.style.display="none",this._titleEl.textContent=this.options.labels.empty,this._titleEl.removeAttribute("title"),this._statsEl.innerHTML="",this._statsEl.removeAttribute("title"),this._crops=[],this._off=0,this._demLoading=!1,this._updateZoomButtons(),this._clearFocus(),this.element.style.display="none",this._adjustAttribution()}}return F.addTheme=(t,e)=>{c[t]=e},F.THEMES=c,F.DEM_PRESETS=w,F.DemSampler=B,F.POSITIONS=u,F.version="2.1.2",F});
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ol-elevation-profile",
|
|
3
|
-
"version": "2.1.
|
|
3
|
+
"version": "2.1.2",
|
|
4
4
|
"description": "Synchronized elevation profile control for OpenLayers, rendered with d3. Reads elevation from 3D GPX/GeoJSON, or fills it from a terrain model: AWS tiles, IGN RGE ALTI, XYZ, WMS, GeoTIFF, GeoServer, or your own source.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/ol-elevation-profile.js",
|
|
@@ -114,7 +114,8 @@ import * as d3 from 'd3';
|
|
|
114
114
|
yTicks: null,
|
|
115
115
|
verticalScale: 'auto', // 'auto' : le profil remplit la hauteur ;
|
|
116
116
|
// un nombre : mètres par centimètre physique ;
|
|
117
|
-
// { exaggeration } : rapport fixe vertical/horizontal
|
|
117
|
+
// { exaggeration } : rapport fixe vertical/horizontal ;
|
|
118
|
+
// { maxExaggeration } : 'auto' sans dépasser ce rapport
|
|
118
119
|
show: 'click',
|
|
119
120
|
showWithoutElevation: true, // trace sans Z, et aucun MNT n'a pu en fournir :
|
|
120
121
|
// le panneau paraît quand même, avec un message
|
|
@@ -836,16 +837,22 @@ import * as d3 from 'd3';
|
|
|
836
837
|
* @property {number} [smoothing=0] Elevation smoothing window, in METERS (0 = none).
|
|
837
838
|
* @property {?number} [xTicks=null] X axis ticks (null = auto from width).
|
|
838
839
|
* @property {?number} [yTicks=null] Y axis ticks (null = auto from height).
|
|
839
|
-
* @property {('auto'|number|{exaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
840
|
+
* @property {('auto'|number|{exaggeration:number}|{maxExaggeration:number})} [verticalScale='auto'] `'auto'`: the
|
|
840
841
|
* profile fills the height, which is legible but changes scale from one track to the
|
|
841
842
|
* next, so a 2 % ramp looks like a wall and two profiles cannot be compared. A number
|
|
842
843
|
* fixes the metres covered per physical centimetre, which makes RANGES comparable.
|
|
843
844
|
* `{exaggeration}` fixes the ratio between the two axes instead, which makes SLOPES
|
|
844
845
|
* comparable: the gradient read off the chart is the real one, multiplied by the same
|
|
845
846
|
* factor on every track, and the control recomputes it per track and per A/B crop.
|
|
846
|
-
*
|
|
847
|
-
*
|
|
848
|
-
*
|
|
847
|
+
* `{maxExaggeration}` keeps `'auto'` — the height is filled, which reads best — and
|
|
848
|
+
* only reins in the absurd: a short, gently sloping track whose 2 % ramp would
|
|
849
|
+
* otherwise be drawn as a wall. A track already under the cap is untouched, so unlike
|
|
850
|
+
* a fixed exaggeration it never flattens a mountain traverse to fit a rule.
|
|
851
|
+
* A number or `{exaggeration}` is a **floor**, not a cage: a track whose range exceeds
|
|
852
|
+
* what the height can show would spill out of the frame, which is worse than losing
|
|
853
|
+
* comparability, so the scale then widens silently, nothing being drawn on the chart
|
|
854
|
+
* to say so. The extra room the scale asks for is added ABOVE the track, never below:
|
|
855
|
+
* centring it would push the axis under sea level on a mountain profile.
|
|
849
856
|
* @property {'click'|'mouseover'} [show='click'] How a track is selected on the map.
|
|
850
857
|
* @property {boolean} [showWithoutElevation=true] What to do with a track that ends up
|
|
851
858
|
* with no elevation at all: none in its geometry, and none the terrain model could
|
|
@@ -1505,23 +1512,44 @@ import * as d3 from 'd3';
|
|
|
1505
1512
|
// La publier partout est le seul moyen de voir la différence plutôt que d'y croire.
|
|
1506
1513
|
const rapport = (etendue) => (cmH > 0 && etendue > 0) ? (s.distance / cmH) / (etendue / cm) : null;
|
|
1507
1514
|
|
|
1508
|
-
|
|
1515
|
+
let vs = this._verticalScaleFor(s, innerW);
|
|
1509
1516
|
if (!(vs > 0)) {
|
|
1510
1517
|
// `'auto'` : la hauteur est remplie, donc c'est l'amplitude qui décide de tout.
|
|
1511
1518
|
// `nice()` arrondit le domaine vers l'extérieur, d'où la lecture APRÈS coup.
|
|
1512
1519
|
const echelle = d3.scaleLinear().domain([bas, haut]).range([innerH, 0]).nice();
|
|
1513
1520
|
const dom = echelle.domain();
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
|
|
1521
|
+
const obtenu = rapport(dom[1] - dom[0]);
|
|
1522
|
+
// Un PLAFOND d'exagération, s'il en est demandé un. Remplir la hauteur est ce
|
|
1523
|
+
// qui se lit le mieux, mais sur une trace courte et peu accidentée cela dresse
|
|
1524
|
+
// une pente de 2 % en muraille. Le plafond n'intervient que là : quand le
|
|
1525
|
+
// remplissage dépasse le rapport permis, on élargit l'échelle jusqu'à lui. Une
|
|
1526
|
+
// trace assez accidentée pour rester en dessous n'est jamais aplatie, ce qu'une
|
|
1527
|
+
// exagération FIXE lui imposerait — à 680 km d'une traversée, elle n'occuperait
|
|
1528
|
+
// plus qu'un dixième du cadre.
|
|
1529
|
+
const plafond = this._plafondExageration();
|
|
1530
|
+
if (!(plafond > 0) || obtenu == null || obtenu <= plafond) {
|
|
1531
|
+
this._vScale = null; // aucune échelle absolue demandée
|
|
1532
|
+
this._vExaggeration = obtenu;
|
|
1533
|
+
return echelle;
|
|
1534
|
+
}
|
|
1535
|
+
vs = (s.distance / cmH) / plafond; // l'échelle qui donne exactement le plafond
|
|
1517
1536
|
}
|
|
1518
1537
|
const etendue = Math.max(vs * cm, haut - bas); // jamais moins qu'il n'en faut
|
|
1519
|
-
const milieu = (bas + haut) / 2;
|
|
1520
1538
|
this._vScale = etendue / cm; // m/cm effectivement appliqués
|
|
1521
1539
|
// Sous le plancher, le rapport retombe sous celui demandé : c'est la seule façon de
|
|
1522
1540
|
// savoir que c'est arrivé.
|
|
1523
1541
|
this._vExaggeration = rapport(etendue);
|
|
1524
|
-
|
|
1542
|
+
|
|
1543
|
+
// La marge que l'échelle impose se place AU-DESSUS, pas de part et d'autre.
|
|
1544
|
+
// Centrer la fenêtre creuse sous la trace : une échelle large - ce que demande
|
|
1545
|
+
// une exagération fixe sur une trace longue - fait alors descendre l'axe sous le
|
|
1546
|
+
// niveau de la mer, et on lit « -900 m » sur un profil de montagne. Le plancher
|
|
1547
|
+
// est donc zéro, ou le point le plus bas de la trace s'il passe dessous : une
|
|
1548
|
+
// dépression existe, une altitude négative inventée, non.
|
|
1549
|
+
const plancher = Math.min(0, bas);
|
|
1550
|
+
let y0 = (bas + haut) / 2 - etendue / 2; // le centrage, quand il tient
|
|
1551
|
+
if (y0 < plancher) y0 = plancher;
|
|
1552
|
+
return d3.scaleLinear().domain([y0, y0 + etendue]).range([innerH, 0]);
|
|
1525
1553
|
}
|
|
1526
1554
|
|
|
1527
1555
|
/**
|
|
@@ -1539,6 +1567,13 @@ import * as d3 from 'd3';
|
|
|
1539
1567
|
*
|
|
1540
1568
|
* @private
|
|
1541
1569
|
*/
|
|
1570
|
+
/** Le rapport à ne pas dépasser, `0` s'il n'en est pas demandé. @private */
|
|
1571
|
+
_plafondExageration() {
|
|
1572
|
+
const v = this.options.verticalScale;
|
|
1573
|
+
const n = (v && typeof v === 'object') ? Number(v.maxExaggeration) : 0;
|
|
1574
|
+
return n > 0 ? n : 0;
|
|
1575
|
+
}
|
|
1576
|
+
|
|
1542
1577
|
_verticalScaleFor(s, innerW) {
|
|
1543
1578
|
const v = this.options.verticalScale;
|
|
1544
1579
|
if (typeof v === 'number') return v;
|
|
@@ -1748,7 +1783,9 @@ import * as d3 from 'd3';
|
|
|
1748
1783
|
this._statsEl.setAttribute('title', text.join(' · '));
|
|
1749
1784
|
|
|
1750
1785
|
this._legendEl.innerHTML = '';
|
|
1751
|
-
|
|
1786
|
+
// Une légende de pentes sans altitude ne légende rien : elle annoncerait des
|
|
1787
|
+
// classes qu'aucun trait ne porte, sous un panneau qui dit n'avoir pas de profil.
|
|
1788
|
+
if (o.slope && o.slopeLegend && !sansAltimetrie) {
|
|
1752
1789
|
const sc = this._slopeScale();
|
|
1753
1790
|
for (let idx = 0; idx <= sc.maxIdx; idx++) {
|
|
1754
1791
|
const color = sc.colorByIndex(idx);
|