@geoblocks/elevation-profile 0.0.2 → 0.0.4
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/elevation-profile.d.ts +3 -2
- package/dist/elevation-profile.d.ts.map +1 -1
- package/dist/elevation-profile.js +14 -7
- package/dist/elevation-profile.js.map +1 -1
- package/dist/index.600fa9d1.js +5245 -0
- package/dist/index.600fa9d1.js.map +1 -0
- package/dist/index.html +574 -0
- package/elevation-profile.ts +62 -36
- package/package.json +1 -1
package/elevation-profile.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import {LitElement, svg} from 'lit';
|
|
2
2
|
import {customElement, state, property} from 'lit/decorators.js';
|
|
3
3
|
import {ResizeController} from '@lit-labs/observers/resize-controller.js';
|
|
4
|
-
import {
|
|
4
|
+
import type {PropertyValues} from 'lit';
|
|
5
5
|
|
|
6
6
|
import {extent, bisector} from 'd3-array';
|
|
7
7
|
import {scaleLinear} from 'd3-scale';
|
|
@@ -9,6 +9,7 @@ import {line, area} from 'd3-shape';
|
|
|
9
9
|
import {axisBottom, axisLeft} from 'd3-axis';
|
|
10
10
|
import {select, pointer} from 'd3-selection';
|
|
11
11
|
|
|
12
|
+
type PlotPoint = number[];
|
|
12
13
|
|
|
13
14
|
@customElement('elevation-profile')
|
|
14
15
|
export class ElevationProfile extends LitElement {
|
|
@@ -17,42 +18,49 @@ export class ElevationProfile extends LitElement {
|
|
|
17
18
|
@property({type: Object}) tickSize = {x: 100, y: 40};
|
|
18
19
|
|
|
19
20
|
@state() pointer = {x: 0, y: 0};
|
|
20
|
-
private
|
|
21
|
+
private _resizeController = new ResizeController(this, {});
|
|
21
22
|
|
|
22
|
-
private plotData:
|
|
23
|
+
private plotData: PlotPoint[] = [];
|
|
23
24
|
private scaleX = scaleLinear();
|
|
24
25
|
private scaleY = scaleLinear();
|
|
25
26
|
|
|
26
|
-
private bisectDistance = bisector((
|
|
27
|
+
private bisectDistance = bisector((point: PlotPoint) => point[0]);
|
|
27
28
|
|
|
28
29
|
private line = line()
|
|
29
|
-
.x((point) => this.scaleX(point[0]))
|
|
30
|
-
.y((point) => this.scaleY(point[1]));
|
|
30
|
+
.x((point: PlotPoint) => this.scaleX(point[0]))
|
|
31
|
+
.y((point: PlotPoint) => this.scaleY(point[1]));
|
|
31
32
|
private area = area()
|
|
32
|
-
.x((point) => this.scaleX(point[0]))
|
|
33
|
-
.y1((point) => this.scaleY(point[1]));
|
|
34
|
-
private xAxis = axisBottom(this.scaleX)
|
|
35
|
-
|
|
36
|
-
private
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
private
|
|
45
|
-
|
|
46
|
-
|
|
33
|
+
.x((point: PlotPoint) => this.scaleX(point[0]))
|
|
34
|
+
.y1((point: PlotPoint) => this.scaleY(point[1]));
|
|
35
|
+
private xAxis = axisBottom(this.scaleX).tickFormat((value: number) => this.tickFormat(value));
|
|
36
|
+
private yAxis = axisLeft(this.scaleY).tickFormat((value: number) => this.tickFormat(value));
|
|
37
|
+
private xGrid = axisBottom(this.scaleX).tickFormat(() => '');
|
|
38
|
+
private yGrid = axisLeft(this.scaleY).tickFormat(() => '');
|
|
39
|
+
|
|
40
|
+
private meterFormat = Intl.NumberFormat('de-CH', {
|
|
41
|
+
style: 'unit',
|
|
42
|
+
unit: 'meter',
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
private kilometerFormat = Intl.NumberFormat('de-CH', {
|
|
46
|
+
style: 'unit',
|
|
47
|
+
unit: 'kilometer',
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
override willUpdate(changedProperties: PropertyValues) {
|
|
47
51
|
if (changedProperties.has('lines')) {
|
|
48
52
|
this.plotData = this.lines.map((coordinate) => [coordinate[3], coordinate[2]]);
|
|
49
53
|
|
|
50
|
-
this.scaleX.domain(extent(this.plotData, (data) => data[0]));
|
|
51
|
-
this.scaleY.domain(extent(this.plotData, (data) => data[1])).nice();
|
|
54
|
+
this.scaleX.domain(extent(this.plotData, (data: PlotPoint) => data[0]));
|
|
55
|
+
this.scaleY.domain(extent(this.plotData, (data: PlotPoint) => data[1])).nice();
|
|
52
56
|
}
|
|
53
57
|
}
|
|
54
58
|
|
|
55
|
-
|
|
59
|
+
// override shouldUpdate(): boolean {
|
|
60
|
+
// return this.lines.length > 0;
|
|
61
|
+
// }
|
|
62
|
+
|
|
63
|
+
override render() {
|
|
56
64
|
const width = this.offsetWidth;
|
|
57
65
|
const height = this.offsetHeight;
|
|
58
66
|
|
|
@@ -71,22 +79,22 @@ export class ElevationProfile extends LitElement {
|
|
|
71
79
|
this.yAxis.ticks(yTicks);
|
|
72
80
|
this.yGrid.ticks(yTicks);
|
|
73
81
|
|
|
74
|
-
select(this.
|
|
75
|
-
select(this.
|
|
76
|
-
select(this.
|
|
77
|
-
select(this.
|
|
82
|
+
select(this.querySelector('.axis.x')).call(this.xAxis);
|
|
83
|
+
select(this.querySelector('.axis.y')).call(this.yAxis);
|
|
84
|
+
select(this.querySelector('.grid.x')).call(this.xGrid);
|
|
85
|
+
select(this.querySelector('.grid.y')).call(this.yGrid);
|
|
78
86
|
|
|
79
87
|
return svg`
|
|
80
|
-
<svg width="${width}" height="${height}">
|
|
81
|
-
<g class="grid y"
|
|
82
|
-
<g class="grid x"
|
|
83
|
-
<g class="axis x"
|
|
84
|
-
<g class="axis y"
|
|
88
|
+
<svg width="${width}" height="${height}" xmlns="http://www.w3.org/2000/svg">
|
|
89
|
+
<g class="grid y" transform="translate(${this.margin.left}, 0)" />
|
|
90
|
+
<g class="grid x" transform="translate(0, ${this.margin.bottom})" />
|
|
91
|
+
<g class="axis x" transform="translate(0, ${height - this.margin.bottom})" />
|
|
92
|
+
<g class="axis y" transform="translate(${this.margin.left}, 0)" />
|
|
85
93
|
<path class="area" d="${this.area(this.plotData)}" />
|
|
86
94
|
<path class="elevation" d="${this.line(this.plotData)}" fill="none" />
|
|
87
95
|
<g style="visibility: ${this.pointer.x > 0 ? 'visible' : 'hidden'}">
|
|
88
96
|
<path class="elevation highlight" d="${this.line(this.plotData)}" fill="none"
|
|
89
|
-
clip-path="polygon(0 0, ${this.pointer.x -
|
|
97
|
+
clip-path="polygon(0 0, ${this.pointer.x - this.margin.left} 0, ${this.pointer.x - this.margin.left} 100%, 0 100%)"
|
|
90
98
|
/>
|
|
91
99
|
<line
|
|
92
100
|
class="pointer-line y"
|
|
@@ -102,6 +110,7 @@ export class ElevationProfile extends LitElement {
|
|
|
102
110
|
height="${height}"
|
|
103
111
|
fill="none"
|
|
104
112
|
pointer-events="all"
|
|
113
|
+
style="touch-action: none;"
|
|
105
114
|
@pointermove="${this.pointerMove}"
|
|
106
115
|
@pointerout="${this.pointerOut}"
|
|
107
116
|
/>
|
|
@@ -109,9 +118,26 @@ export class ElevationProfile extends LitElement {
|
|
|
109
118
|
`;
|
|
110
119
|
}
|
|
111
120
|
|
|
121
|
+
private tickFormat(value: number) {
|
|
122
|
+
if (value < 1000) {
|
|
123
|
+
return this.meterFormat.format(value);
|
|
124
|
+
} else {
|
|
125
|
+
return this.kilometerFormat.format(value / 1000);
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
override firstUpdated() {
|
|
130
|
+
// FIXME: because the ref element are used before render is done, we need to force an update
|
|
131
|
+
this.requestUpdate();
|
|
132
|
+
}
|
|
133
|
+
|
|
112
134
|
private pointerMove(event: PointerEvent) {
|
|
113
135
|
const pointerDistance = this.scaleX.invert(pointer(event)[0]);
|
|
114
|
-
const index = Math.min(this.bisectDistance(this.plotData, pointerDistance), this.plotData.length - 1);
|
|
136
|
+
const index = Math.min(this.bisectDistance.left(this.plotData, pointerDistance), this.plotData.length - 1);
|
|
137
|
+
|
|
138
|
+
if (index < 0) {
|
|
139
|
+
return;
|
|
140
|
+
}
|
|
115
141
|
// FIXME:
|
|
116
142
|
// var d0 = data[i - 1]
|
|
117
143
|
// var d1 = data[i];
|
|
@@ -143,7 +169,7 @@ export class ElevationProfile extends LitElement {
|
|
|
143
169
|
this.dispatchEvent(new CustomEvent('out'));
|
|
144
170
|
}
|
|
145
171
|
|
|
146
|
-
createRenderRoot() {
|
|
172
|
+
override createRenderRoot() {
|
|
147
173
|
return this;
|
|
148
174
|
}
|
|
149
175
|
}
|