move crosshair on trail hover
This commit is contained in:
@@ -2,7 +2,7 @@ import { type ControlPosition, type IControl } from "maplibre-gl";
|
||||
import * as M from "maplibre-gl";
|
||||
import { ElevationProfile, type ElevationProfileOptions } from "./elevationprofile";
|
||||
// @ts-ignore
|
||||
import type { GeoJsonObject } from "geojson";
|
||||
import type { GeoJsonObject, Position } from "geojson";
|
||||
import type { Waypoint } from "$lib/models/waypoint";
|
||||
|
||||
/**
|
||||
@@ -189,6 +189,30 @@ export class ElevationProfileControl implements IControl {
|
||||
this.isProfileShown = false;
|
||||
}
|
||||
|
||||
moveCrosshair(lat: number, lon: number) {
|
||||
if (!this.elevationProfileChart) {
|
||||
return;
|
||||
}
|
||||
const chart = this.elevationProfileChart.chart
|
||||
const point = this.elevationProfileChart.getChartCoordinatesFromPosition(lat, lon)
|
||||
if (point == null) {
|
||||
return;
|
||||
}
|
||||
const rectangle = chart.canvas.getBoundingClientRect();
|
||||
|
||||
const mouseMoveEvent = new MouseEvent('mousemove', {
|
||||
clientX: rectangle.left + point[0],
|
||||
clientY: rectangle.top + point[1]
|
||||
});
|
||||
|
||||
chart.canvas.dispatchEvent(mouseMoveEvent);
|
||||
}
|
||||
|
||||
hideCrosshair() {
|
||||
const mouseOutEvent = new MouseEvent('mouseout');
|
||||
return this.elevationProfileChart?.chart.canvas.dispatchEvent(mouseOutEvent);
|
||||
}
|
||||
|
||||
onRemove(): void {
|
||||
// remove button
|
||||
if (this.buttonContainer?.parentNode) {
|
||||
|
||||
@@ -358,7 +358,7 @@ const elevationProfileDefaultOptions: ElevationProfileOptions = {
|
||||
export class ElevationProfile {
|
||||
private canvas: HTMLCanvasElement;
|
||||
private settings: ElevationProfileOptions;
|
||||
private chart: Chart<"line", Array<number>, number>;
|
||||
public chart: Chart<"line", Array<number>, number>;
|
||||
private elevatedPositions: Position[] = [];
|
||||
private elevatedPositionsAdjustedUnit: Position[] = [];
|
||||
private cumulatedDistance: number[] = [];
|
||||
@@ -483,7 +483,6 @@ export class ElevationProfile {
|
||||
},
|
||||
onHover: (_e, item) => {
|
||||
if (typeof this.settings.onMove !== "function") return;
|
||||
|
||||
try {
|
||||
const i = item[0].index;
|
||||
|
||||
@@ -753,6 +752,33 @@ export class ElevationProfile {
|
||||
}
|
||||
}
|
||||
|
||||
getChartCoordinatesFromPosition(lat: number, lon: number) {
|
||||
|
||||
let minDistance = Infinity
|
||||
let bestCandiateIndex: number = -1
|
||||
for (let i = 0; i < this.elevatedPositionsAdjustedUnit.length; i++) {
|
||||
const p = this.elevatedPositionsAdjustedUnit[i];
|
||||
const deltaLat = lat - p[1];
|
||||
const deltaLon = lon - p[0];
|
||||
const distance = deltaLat * deltaLat + deltaLon * deltaLon;
|
||||
|
||||
if (distance < minDistance) {
|
||||
minDistance = distance;
|
||||
bestCandiateIndex = i
|
||||
}
|
||||
};
|
||||
|
||||
if (bestCandiateIndex < 0) {
|
||||
return null;
|
||||
}
|
||||
const meta = this.chart.getDatasetMeta(0);
|
||||
const element = meta.data[bestCandiateIndex];
|
||||
if (element) {
|
||||
return [element.x, element.y];
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
gradientFromElevation(chart: Chart, force: boolean = false) {
|
||||
const ctx = chart.ctx;
|
||||
const chartArea = chart.chartArea;
|
||||
@@ -864,7 +890,7 @@ export class ElevationProfile {
|
||||
async setData(data: GeoJsonObject, waypoints?: Waypoint[]) {
|
||||
// Concatenates the positions that may come from multiple LineStrings or MultiLineString
|
||||
const { positions, times } = geoJsonObjectToPositionsAndTimes(data);
|
||||
|
||||
|
||||
this.times = times;
|
||||
|
||||
this.elevatedPositions = smoothElevations(positions, Math.ceil(positions.length / 100));
|
||||
@@ -954,14 +980,17 @@ export class ElevationProfile {
|
||||
|
||||
const timeStart = this.times[segmentStartIndex]
|
||||
const timeEnd = this.times[i]
|
||||
const timeDelta = (timeEnd.getTime() - timeStart.getTime()) / 1000
|
||||
if (timeStart && timeEnd) {
|
||||
const timeDelta = (timeEnd.getTime() - timeStart.getTime()) / 1000
|
||||
|
||||
speed = (distanceDelta / timeDelta)
|
||||
if (this.settings.unit === "imperial") {
|
||||
speed = speed * MILES_HOUR_PER_METER_SECOND
|
||||
} else {
|
||||
speed = speed * KILOMETERS_HOUR_PER_METER_SECOND;
|
||||
speed = (distanceDelta / timeDelta)
|
||||
if (this.settings.unit === "imperial") {
|
||||
speed = speed * MILES_HOUR_PER_METER_SECOND
|
||||
} else {
|
||||
speed = speed * KILOMETERS_HOUR_PER_METER_SECOND;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user