From b5fd8ea09ba6bb0a897f5e56313fd92242b714b4 Mon Sep 17 00:00:00 2001 From: vcoppe Date: Thu, 22 Aug 2024 10:41:04 +0200 Subject: [PATCH 1/4] refine routing controls interactions --- gpx/src/gpx.ts | 8 +++++++- .../toolbar/tools/routing/RoutingControls.ts | 15 ++++++++++++--- website/src/lib/utils.ts | 13 +++++++++---- 3 files changed, 28 insertions(+), 8 deletions(-) diff --git a/gpx/src/gpx.ts b/gpx/src/gpx.ts index 54612f18..cb11066a 100644 --- a/gpx/src/gpx.ts +++ b/gpx/src/gpx.ts @@ -1360,7 +1360,13 @@ export class GPXStatistics { } const earthRadius = 6371008.8; -export function distance(coord1: Coordinates, coord2: Coordinates): number { +export function distance(coord1: TrackPoint | Coordinates, coord2: TrackPoint | Coordinates): number { + if (coord1 instanceof TrackPoint) { + coord1 = coord1.getCoordinates(); + } + if (coord2 instanceof TrackPoint) { + coord2 = coord2.getCoordinates(); + } const rad = Math.PI / 180; const lat1 = coord1.lat * rad; const lat2 = coord2.lat * rad; diff --git a/website/src/lib/components/toolbar/tools/routing/RoutingControls.ts b/website/src/lib/components/toolbar/tools/routing/RoutingControls.ts index ec118d16..08b21755 100644 --- a/website/src/lib/components/toolbar/tools/routing/RoutingControls.ts +++ b/website/src/lib/components/toolbar/tools/routing/RoutingControls.ts @@ -334,14 +334,14 @@ export class RoutingControls { let file = get(this.file)?.file; // Find the point closest to the temporary anchor - let minDistance = Number.MAX_VALUE; + let minDetails: any = { distance: Number.MAX_VALUE }; let minAnchor = this.temporaryAnchor as Anchor; file?.forEachSegment((segment, trackIndex, segmentIndex) => { if (get(selection).hasAnyParent(new ListTrackSegmentItem(this.fileId, trackIndex, segmentIndex))) { let details: any = {}; let closest = getClosestLinePoint(segment.trkpt, this.temporaryAnchor.point, details); - if (details.distance < minDistance) { - minDistance = details.distance; + if (details.distance < minDetails.distance) { + minDetails = details; minAnchor = { point: closest, segment, @@ -352,6 +352,15 @@ export class RoutingControls { } }); + if (minAnchor.point._data.anchor) { + minAnchor.point = minAnchor.point.clone(); + if (minDetails.before) { + minAnchor.point._data.index = minAnchor.point._data.index + 0.5; + } else { + minAnchor.point._data.index = minAnchor.point._data.index - 0.5; + } + } + return minAnchor; } diff --git a/website/src/lib/utils.ts b/website/src/lib/utils.ts index 3542aae4..1e0d6e40 100644 --- a/website/src/lib/utils.ts +++ b/website/src/lib/utils.ts @@ -5,11 +5,10 @@ import type { TransitionConfig } from "svelte/transition"; import { get } from "svelte/store"; import { map } from "./stores"; import { base } from "$app/paths"; -import { browser } from "$app/environment"; import { languages } from "$lib/languages"; -import { locale } from "svelte-i18n"; +import { locale, t } from "svelte-i18n"; import type mapboxgl from "mapbox-gl"; -import { type TrackPoint, type Coordinates, crossarcDistance } from "gpx"; +import { type TrackPoint, type Coordinates, crossarcDistance, distance } from "gpx"; export function cn(...inputs: ClassValue[]) { return twMerge(clsx(inputs)); @@ -75,8 +74,14 @@ export function getClosestLinePoint(points: TrackPoint[], point: TrackPoint | Co for (let i = 0; i < points.length - 1; i++) { let dist = crossarcDistance(points[i], points[i + 1], point); if (dist < closestDist) { - closest = points[i]; closestDist = dist; + if (distance(points[i], point) <= distance(points[i + 1], point)) { + closest = points[i]; + details['before'] = true; + } else { + closest = points[i + 1]; + details['before'] = false; + } } } details['distance'] = closestDist; From e10e2412c43ac8ac5799fc09dcaf03f778f4d62c Mon Sep 17 00:00:00 2001 From: vcoppe Date: Thu, 22 Aug 2024 11:33:11 +0200 Subject: [PATCH 2/4] fix timestamp edition for files with missing ones --- gpx/src/gpx.ts | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/gpx/src/gpx.ts b/gpx/src/gpx.ts index cb11066a..912cf982 100644 --- a/gpx/src/gpx.ts +++ b/gpx/src/gpx.ts @@ -784,7 +784,7 @@ export class TrackSegment extends GPXTreeLeaf { let start = simplified[i].point._data.index; let end = simplified[i + 1].point._data.index; let dist = statistics.local.distance.total[end] - statistics.local.distance.total[start]; - let ele = simplified[i + 1].point.ele - simplified[i].point.ele; + let ele = (simplified[i + 1].point.ele ?? 0) - (simplified[i].point.ele ?? 0); for (let j = start; j < end + (i + 1 === simplified.length - 1 ? 1 : 0); j++) { slope.push(0.1 * ele / dist); @@ -1418,9 +1418,15 @@ function withTimestamps(points: TrackPoint[], speed: number, lastPoint: TrackPoi function withShiftedAndCompressedTimestamps(points: TrackPoint[], speed: number, ratio: number, lastPoint: TrackPoint): TrackPoint[] { let start = getTimestamp(lastPoint, points[0], speed); + let last = points[0]; return points.map((point) => { let pt = point.clone(); - pt.time = new Date(start.getTime() + ratio * (point.time.getTime() - points[0].time.getTime())); + if (point.time === undefined) { + pt.time = getTimestamp(last, point, speed); + } else { + pt.time = new Date(start.getTime() + ratio * (point.time.getTime() - points[0].time.getTime())); + } + last = pt; return pt; }); } From e42dd6e144f82e5410fe0f802c9da92072078cdf Mon Sep 17 00:00:00 2001 From: vcoppe Date: Thu, 22 Aug 2024 14:56:39 +0200 Subject: [PATCH 3/4] fix stats slice bug, closes #67 --- gpx/src/gpx.ts | 11 +++++++++++ .../components/toolbar/tools/scissors/Scissors.svelte | 6 +++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/gpx/src/gpx.ts b/gpx/src/gpx.ts index 912cf982..2d06ae6e 100644 --- a/gpx/src/gpx.ts +++ b/gpx/src/gpx.ts @@ -1326,6 +1326,17 @@ export class GPXStatistics { } slice(start: number, end: number): GPXStatistics { + if (start < 0) { + start = 0; + } else if (start >= this.local.points.length) { + return new GPXStatistics(); + } + if (end < start) { + return new GPXStatistics(); + } else if (end >= this.local.points.length) { + end = this.local.points.length - 1; + } + let statistics = new GPXStatistics(); statistics.local.points = this.local.points.slice(start, end + 1); diff --git a/website/src/lib/components/toolbar/tools/scissors/Scissors.svelte b/website/src/lib/components/toolbar/tools/scissors/Scissors.svelte index 9c51406b..05ff6143 100644 --- a/website/src/lib/components/toolbar/tools/scissors/Scissors.svelte +++ b/website/src/lib/components/toolbar/tools/scissors/Scissors.svelte @@ -37,8 +37,8 @@ $selection.hasAnyChildren(new ListRootItem(), true, ['waypoints']) && $gpxStatistics.local.points.length > 0; - let maxSliderValue = 100; - let sliderValues = [0, 100]; + let maxSliderValue = 1; + let sliderValues = [0, 1]; function updateCanCrop() { canCrop = sliderValues[0] != 0 || sliderValues[1] != maxSliderValue; @@ -66,7 +66,7 @@ if (validSelection && $gpxStatistics.local.points.length > 0) { maxSliderValue = $gpxStatistics.local.points.length - 1; } else { - maxSliderValue = 100; + maxSliderValue = 1; } await tick(); sliderValues = [0, maxSliderValue]; From c1faea787a16fc92c7893354806993809fb1274c Mon Sep 17 00:00:00 2001 From: vcoppe Date: Fri, 23 Aug 2024 10:31:02 +0200 Subject: [PATCH 4/4] block delete shortcut when focusing an input #68 --- website/src/lib/components/Menu.svelte | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/website/src/lib/components/Menu.svelte b/website/src/lib/components/Menu.svelte index 5ca99121..d0c89315 100644 --- a/website/src/lib/components/Menu.svelte +++ b/website/src/lib/components/Menu.svelte @@ -499,12 +499,14 @@ dbUtils.undo(); } } else if ((e.key === 'Backspace' || e.key === 'Delete') && (e.metaKey || e.ctrlKey)) { - if (e.shiftKey) { - dbUtils.deleteAllFiles(); - } else { - dbUtils.deleteSelection(); + if (!targetInput) { + if (e.shiftKey) { + dbUtils.deleteAllFiles(); + } else { + dbUtils.deleteSelection(); + } + e.preventDefault(); } - e.preventDefault(); } else if (e.key === 'a' && (e.metaKey || e.ctrlKey)) { if (!targetInput) { selectAll();