Create markers with custom views

You can use Marker to render custom SwiftUI View hierarchies as markers on a 3D Map. Custom view markers let you display rich SwiftUI layouts, interactive controls, and animations anchored to geographic coordinates.

Add a custom view marker

To add a custom view marker to your Map, declare a Marker inside the map content builder, specify its position using a LatLngAltitude value, and provide your custom SwiftUI View in the trailing content closure.

If you omit the content closure, Marker renders a default Pin view.

import GoogleMaps3D
import SwiftUI

struct CustomMarkerExampleView: View {
  var body: some View {
    Map(mode: .hybrid) {
      Marker(
        position: LatLngAltitude(
          latitude: 40.7484,
          longitude: -73.9857,
          altitude: 100.0
        ),
        altitudeMode: .relativeToGround
      ) {
        Text("Empire State Building")
          .padding(.horizontal, 12)
          .padding(.vertical, 6)
          .background(Color.white)
          .clipShape(Capsule())
      }
    }
  }
}

Customize the default Pin view

Instead of building a completely custom SwiftUI View, you can render a customized pin by passing a Pin initialized with a Pin.Configuration to the Marker content closure:

import GoogleMaps3D
import SwiftUI

struct CustomPinMarkerExampleView: View {
  var body: some View {
    Map(mode: .hybrid) {
      Marker(
        position: LatLngAltitude(
          latitude: 40.7484,
          longitude: -73.9857,
          altitude: 100.0
        ),
        altitudeMode: .relativeToGround
      ) {
        Pin(
          configuration: .init(
            backgroundColor: .blue,
            borderColor: .white
          )
        )
      }
    }
  }
}

Handle interactions and animations

Because Marker hosts a SwiftUI View, you can attach standard SwiftUI gesture modifiers (such as .onTapGesture) and SwiftUI animations directly to the view inside the Marker content closure.

In addition, Marker conforms to MapContentAnchorable, which lets you anchor a Popover to the marker using the popover(isOpen:autoClosedEnabled:autoPanEnabled:style:content:) modifier:

import GoogleMaps3D
import SwiftUI

struct InteractiveMarkerExampleView: View {
  @State private var isPopoverOpen = false

  var body: some View {
    Map(mode: .hybrid) {
      Marker(
        position: LatLngAltitude(
          latitude: 37.7955,
          longitude: -122.3937,
          altitude: 0
        ),
        altitudeMode: .relativeToGround
      ) {
        Pin(configuration: .init(backgroundColor: .black) {
          Image(systemName: "ferry.fill")
            .foregroundStyle(.white)
        })
        .onTapGesture {
          isPopoverOpen.toggle()
        }
      }
      .popover(isOpen: $isPopoverOpen) {
        Text("Ferry Building")
      }
    }
  }
}

Configure altitude and collision behavior

You can customize how a Marker is positioned vertically and how it interacts with overlapping map labels or markers by passing parameters to Marker.init: