From 8c2e7eb6ab84019304f110cd50b05dcf725a1dfc Mon Sep 17 00:00:00 2001 From: hermes-explorigin Date: Sun, 9 Aug 2026 16:01:47 +0000 Subject: [PATCH] Directions: add Imperial unit system (feet/miles) alongside metric - Add a System selector (Metric/Imperial) to the Directions panel; Units dropdown adapts (m/km vs ft/mi) with a smart Auto for each system - Auto: short routes show the small unit (m or ft), long routes the large one (km or mi); shows the alternate unit as a sub-line - README: document the unit system + units options --- README.md | 5 +- src/lib/components/DirectionsPanel.svelte | 79 ++++++++++++++++++----- 2 files changed, 67 insertions(+), 17 deletions(-) diff --git a/README.md b/README.md index 695c380..da50eb0 100644 --- a/README.md +++ b/README.md @@ -230,8 +230,9 @@ button appears in the top bar. Opening it lets you: - **Avoid certain POI categories** along the route (schools, fire stations, fuel stations, parking, restaurants, …). - **Compute** a route and **draw it** on the map. -- Choose **distance units** (`m` / `km`, or `Auto` — meters under 1 km, - kilometers otherwise) and a **travel mode** (Drive or Walk). +- Choose a **unit system** (Metric or Imperial) and **units** (`m`/`km` or + `ft`/`mi`, or `Auto` — which uses the small unit for short routes and the + large one for long routes), plus a **travel mode** (Drive or Walk). - See the route's **distance** and an **estimated travel time** (computed from the mode's average speed). diff --git a/src/lib/components/DirectionsPanel.svelte b/src/lib/components/DirectionsPanel.svelte index 6a7ddb0..f804b4b 100644 --- a/src/lib/components/DirectionsPanel.svelte +++ b/src/lib/components/DirectionsPanel.svelte @@ -22,8 +22,11 @@ let computing = $state(false); let picking: 'from' | 'to' | null = $state(null); - // Units for distance output: 'auto' (m if < 1km else km), 'm', or 'km'. - let unit = $state<'auto' | 'm' | 'km'>('auto'); + // Unit system (Metric or Imperial) and a granular unit override. + // - system 'metric' -> units m / km ; Auto = meters if < 1 km else km + // - system 'imperial'-> units ft / mi ; Auto = feet if < 1/10 mi else mi + let system = $state<'metric' | 'imperial'>('metric'); + let unit = $state<'auto' | 'm' | 'km' | 'ft' | 'mi'>('auto'); // Travel-time mode: average speed (km/h) used for the estimate. let mode = $state<'drive' | 'walk'>('drive'); const SPEEDS = { drive: 45, walk: 4.8 }; // km/h @@ -40,16 +43,52 @@ ]; const selected = $state>({}); - // Format distance in meters/km according to the selected unit. + // Format a metric distance (meters) into the chosen unit system. function formatDistance(m: number): string { - if (unit === 'm' || (unit === 'auto' && m < 1000)) { + // Determine effective unit. + if (system === 'imperial') { + const ft = m * 3.28084; + const mi = m / 1609.344; + const useFt = unit === 'ft' || (unit === 'auto' && ft < 528); + if (useFt) { + const v = ft < 10 ? ft.toFixed(1) : Math.round(ft).toString(); + return `${v} ft`; + } + // miles + return mi < 10 ? `${mi.toFixed(2)} mi` : `${mi.toFixed(1)} mi`; + } + // metric + const useM = unit === 'm' || (unit === 'auto' && m < 1000); + if (useM) { const v = m < 10 ? m.toFixed(1) : Math.round(m).toString(); return `${v} m`; } // km const km = m / 1000; - const v = km < 10 ? km.toFixed(2) : km.toFixed(1); - return `${v} km`; + return km < 10 ? `${km.toFixed(2)} km` : `${km.toFixed(1)} km`; + } + + // Show the alternate unit alongside the chosen one (e.g. "3.31 mi (5.33 km)"). + function formatAlt(m: number): string | null { + if (unit !== 'auto') { + // mirror in the other system once + if (system === 'metric') { + if (unit === 'm') return `${(m / 1000).toFixed(2)} km`; + if (unit === 'km') return m < 1000 ? `${Math.round(m)} m` : null; + return null; + } else { + if (unit === 'ft') return `${(m / 1609.344).toFixed(2)} mi`; + if (unit === 'mi') return ftAlt(m); + return null; + } + } + // Auto: show the other cheaply for long routes + if (system === 'metric') return m >= 1000 ? `${Math.round(m)} m` : null; + return m >= 160.934 ? `${Math.round(m * 3.28084)} ft` : null; + } + function ftAlt(m: number): string | null { + const ft = m * 3.28084; + return ft >= 528 ? null : `${Math.round(ft)} ft`; } // Estimate travel time (minutes) from distance + mode speed. @@ -174,13 +213,25 @@ {/each} -
+
+
+ + +
@@ -205,9 +256,7 @@ Distance {formatDistance(result.distanceM)}
- {#if result.distanceM >= 1000 && unit === 'km'} -
({Math.round(result.distanceM)} m)
- {/if} + {#if formatAlt(result.distanceM)}
{formatAlt(result.distanceM)}
{/if}
Est. time {formatTime(result.distanceM)} @@ -225,7 +274,7 @@