From 52934a83266b71cf4cb5c6239e4400425f822bd8 Mon Sep 17 00:00:00 2001 From: Maurice Date: Thu, 1 Oct 2026 10:38:29 +0200 Subject: [PATCH] fix(mobile): the map compass stands above the base-layer switcher Beside it the two round controls read as one crowded row over the dock; on the switcher's own left edge, one gap above it, they form a column. --- .../src/mobile/screens/trip/map/MMapArea.tsx | 22 +++++++++---------- .../tests/unit/mobile/trip/MMapArea.test.tsx | 15 +++++-------- 2 files changed, 17 insertions(+), 20 deletions(-) diff --git a/client/src/mobile/screens/trip/map/MMapArea.tsx b/client/src/mobile/screens/trip/map/MMapArea.tsx index 6fbdf688e..9e9133834 100644 --- a/client/src/mobile/screens/trip/map/MMapArea.tsx +++ b/client/src/mobile/screens/trip/map/MMapArea.tsx @@ -21,11 +21,13 @@ import type { ViewportPadding } from '../../../../utils/mapViewport' const NO_POIS: Poi[] = [] /** - * The compass stands one gap to the right of the base-layer switcher both engines draw - * in the bottom left corner. Worked out from the switcher's own numbers rather than - * written down as 70, so moving or resizing the switcher carries the compass along. + * The compass stands one gap above the base-layer switcher both engines draw in the + * bottom left corner, on the same left edge, so the two round controls form a column + * instead of a row. Worked out from the switcher's own numbers, so moving or resizing + * the switcher carries the compass along. */ -const COMPASS_LEFT = MAP_LAYER_SWITCHER_INSET + MAP_ROUND_CONTROL_SIZE + 8 +const COMPASS_LEFT = MAP_LAYER_SWITCHER_INSET +const COMPASS_RAISE = MAP_ROUND_CONTROL_SIZE + 8 /** The safe-area insets at the top and the bottom of the screen, in pixels. */ interface SafeInsets { @@ -436,14 +438,12 @@ export default function MMapArea({ planner, shell }: MMapAreaProps) { )} {/* Compass, GL maps only (Leaflet cannot rotate). Both engines draw the base-layer - switcher in the bottom left corner, so the compass sits beside it rather than in - the corner: at `left-3` it started 8px left of the switcher and ran on under it, - reading as a second button showing through the frosted shell. Same - --bottom-nav-h band as the locate button's `right: 12`, so the round controls - still share one line. The left offset is inline because it is computed from the - switcher's own numbers. */} + switcher in the bottom left corner, so the compass stands on top of it, on the + same left edge: beside it the two read as one crowded row next to the dock. + The offsets are inline because they are computed from the switcher's own + numbers. */} {mapActive && glMap && ( -
+
)} diff --git a/client/tests/unit/mobile/trip/MMapArea.test.tsx b/client/tests/unit/mobile/trip/MMapArea.test.tsx index 75f10c5d2..3912e62c0 100644 --- a/client/tests/unit/mobile/trip/MMapArea.test.tsx +++ b/client/tests/unit/mobile/trip/MMapArea.test.tsx @@ -194,15 +194,12 @@ describe('MMapArea', () => { expect(segment.style.flexGrow).toBe('1') }) - it('FE-MOB-MAPAREA-002: the compass rides the same bottom offset as the locate button', () => { + it('FE-MOB-MAPAREA-002: the compass stands on top of the base-layer switcher', () => { const { container } = renderArea() - // LocationButton hard-codes `right: 12` off the same variable, so matching - // the offset here is what keeps the two round controls on one line. - expect(compassBand(container)?.style.bottom).toBe('calc(var(--bottom-nav-h, 84px) + 12px)') - // Beside the base-layer switcher both engines draw in the corner: its inset, its - // size and one gap. In the corner itself it lay under the switcher's frosted shell. - expect(compassBand(container)?.style.left).toBe(`${MAP_LAYER_SWITCHER_INSET + MAP_ROUND_CONTROL_SIZE + 8}px`) + // The switcher's band, raised by its size and one gap, on the switcher's own left edge. + expect(compassBand(container)?.style.bottom).toBe(`calc(var(--bottom-nav-h, 84px) + ${12 + MAP_ROUND_CONTROL_SIZE + 8}px)`) + expect(compassBand(container)?.style.left).toBe(`${MAP_LAYER_SWITCHER_INSET}px`) expect(compassBand(container)?.className).not.toContain('left-3') }) @@ -347,8 +344,8 @@ describe('MMapArea', () => { for (const shellOver of [{ trTab: 'plan' }, { trTab: 'roadtrip', mapFront: true }] as Partial[]) { const { container, unmount } = renderArea(shellOver) - expect(parseFloat(compassBand(container)?.style.left ?? '0')) - .toBeGreaterThanOrEqual(MAP_LAYER_SWITCHER_INSET + MAP_ROUND_CONTROL_SIZE) + // Above the switcher: raised past its full height, so the two never overlap. + expect(compassBand(container)?.style.bottom).toContain(`+ ${12 + MAP_ROUND_CONTROL_SIZE + 8}px`) // With the renderer mocked, the compass is still the one element in this layer // that sets --bottom-nav-h inline; its left offset joined the same style object. expect(container.querySelectorAll('[style*="--bottom-nav-h"]')).toHaveLength(1)