Skip to content

SwiftUI view annotations claim every touch in their frame, blocking map gestures and annotations beneath #2433

Description

@brightfuture

New Feature

MapViewAnnotation content is arbitrary SwiftUI, and it's common for the visible content not to fill the annotation's frame — a callout anchored above a marker, an L-shaped composition, or any layout that needs padding to position content relative to the anchor point. Today the entire frame behaves as opaque to touches:

  • A tap on a transparent part of the frame never reaches onMapTapGesture. SingleTapGestureHandler only accepts touches where touch.view === mapView (Sources/MapboxMaps/Gestures/GestureHandlers/SingleTapGestureHandler.swift), so once the touch lands on the annotation's hosting view, the map gesture is out.
  • Annotations underneath that transparent region become untappable too, since the topmost annotation view wins hit-testing inside ViewAnnotationsContainer.

allowHitTesting(false) is all-or-nothing, so it can't express "interactive where my content is, transparent everywhere else" — which is exactly what a non-rectangular annotation needs.

Request: let view annotation hit-testing follow the content's own hit-test shape, so the host view declines points the SwiftUI content doesn't claim and touches fall through to annotations below and to the map's own gestures. Opt-in would be fine:

MapViewAnnotation(coordinate: coordinate) { ... }
  .hitTestingMode(.contentShape)  // vs. today's .bounds behaviour

Observed with 11.26.0, SwiftUI Map + MapViewAnnotation.

Why

Any annotation that isn't a filled rectangle silently eats map taps and occludes its neighbours. The workaround is to split one logical piece of UI into several content-sized annotations positioned with variableAnchors offsets — a marker annotation plus a separate callout annotation anchored .bottomLeft to the same coordinate — which duplicates state and forces one expand/collapse animation to be coordinated across two SwiftUI views that can't share @State. PR #2276 requested a related escape hatch (an overridable hitTest on the container), so this doesn't appear to be an isolated need.

Metadata

Metadata

Assignees

No one assigned

    Labels

    auto-triagedAutomatically triaged by AIfeature 🍏When working on a new feature or feature enhancement

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions