地点详情组件
借助地点界面套件中的地点详情组件,您可以添加用于在应用中显示地点详情的单独界面组件。

PlaceDetailsCompactView
会使用最少的空间渲染所选地点的详细信息。这在以下场景中可能很有用:在地图上突出显示地点的信息窗口中;在社交媒体体验中(例如在聊天中分享地点);作为选择当前位置的建议;或在媒体文章中引用 Google 地图上的位置。PlaceDetailsCompactView
可以显示名称、地址、评分、类型、价格、无障碍图标、营业状态和一张照片。
地点详情组件可以单独使用,也可以与其他 Google Maps Platform API 和服务搭配使用。该组件接受地点 ID 或纬度/经度坐标,并返回渲染的地点详情信息。
地点详情组件提供紧凑视图,可水平或垂直显示。
您可以配置地点详情组件的内容和视觉样式,使其符合您的使用情形和视觉品牌推广指南。您可以通过提供自定义 PlacesMaterialTheme
值来自定义地点详情的外观。您还可以通过指定 PlaceDetailsCompactView
条目列表(每个条目对应于显示的地点相关信息)来自定义要包含的地点详情字段。
结算
使用地点详情界面套件时,每次调用 PlaceDetailsQuery
方法都会产生费用。如果您多次加载同一地点,则需要为每次请求付费。
向您的应用添加地点详情
“地点详情”组件是 Swift 界面视图。您可以自定义地点详情信息的外观和风格,以满足您的需求并与应用的外观保持一致。
您可以指定屏幕方向(水平或垂直)、主题替换项和内容。内容选项包括媒体、地址、评分、价格、类型、无障碍入口、地图链接和路线链接。详细了解自定义。
默认位置为竖屏。如果您希望采用横向布局,请在 PlaceDetailsCompactView
中指定 orientation: .horizontal
。
此示例会创建一个采用垂直布局的紧凑视图。
Swift
// Callback for the place details widget. let placeDetailsCallback: (PlaceDetailsResult) -> Void = { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } @Environment(\.colorScheme) var colorScheme var customTheme = false var theme: PlacesMaterialTheme { if customTheme { var theme = PlacesMaterialTheme() var color = PlacesMaterialColor() color.surface = (colorScheme == .dark ? .blue : .gray) color.outlineDecorative = (colorScheme == .dark ? .white : .black) color.onSurface = (colorScheme == .dark ? .yellow : .red) color.onSurfaceVariant = (colorScheme == .dark ? .white : .blue) color.onSecondaryContainer = (colorScheme == .dark ? .white : .red) color.secondaryContainer = (colorScheme == .dark ? .green : .purple) color.positive = (colorScheme == .dark ? .yellow : .red) color.primary = (colorScheme == .dark ? .yellow : .purple) color.info = (colorScheme == .dark ? .yellow : .purple) var shape = PlacesMaterialShape() shape.cornerRadius = 10 var font = PlacesMaterialFont() font.labelLarge = .system(size: UIFontMetrics.default.scaledValue(for: 18)) font.headlineMedium = .system(size: UIFontMetrics.default.scaledValue(for: 15)) font.bodyLarge = .system(size: UIFontMetrics.default.scaledValue(for: 15)) font.bodyMedium = .system(size: UIFontMetrics.default.scaledValue(for: 12)) font.bodySmall = .system(size: UIFontMetrics.default.scaledValue(for: 11)) var attribution = PlacesMaterialAttribution() attribution.lightModeColor = .black attribution.darkModeColor = .white theme.color = color theme.shape = shape theme.font = font theme.attribution = attribution } else { return PlacesMaterialTheme() } } @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID("ChIJT7FdmYiAhYAROFOvrIxRJDU")) var body: some View { PlaceDetailsCompactView( orientation: .vertical, query: $query, contentType: [.media(), .address(), .rating(), .type(), .price(), .accessibleEntranceIcon(), .openNowStatus()], theme: theme, placeDetailsCallback: placeDetailsCallback, preferTruncation: false ) .frame(width: 350) }
此示例会创建一个采用水平布局的紧凑视图。
Swift
// Callback for the place details widget. let placeDetailsCallback: (PlaceDetailsResult) -> Void = { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } @Environment(\.colorScheme) var colorScheme var customTheme = false var theme: PlacesMaterialTheme { if customTheme { var theme = PlacesMaterialTheme() var color = PlacesMaterialColor() color.surface = (colorScheme == .dark ? .blue : .gray) color.outlineDecorative = (colorScheme == .dark ? .white : .black) color.onSurface = (colorScheme == .dark ? .yellow : .red) color.onSurfaceVariant = (colorScheme == .dark ? .white : .blue) color.onSecondaryContainer = (colorScheme == .dark ? .white : .red) color.secondaryContainer = (colorScheme == .dark ? .green : .purple) color.positive = (colorScheme == .dark ? .yellow : .red) color.primary = (colorScheme == .dark ? .yellow : .purple) color.info = (colorScheme == .dark ? .yellow : .purple) var shape = PlacesMaterialShape() shape.cornerRadius = 10 var font = PlacesMaterialFont() font.labelLarge = .system(size: UIFontMetrics.default.scaledValue(for: 18)) font.headlineMedium = .system(size: UIFontMetrics.default.scaledValue(for: 15)) font.bodyLarge = .system(size: UIFontMetrics.default.scaledValue(for: 15)) font.bodyMedium = .system(size: UIFontMetrics.default.scaledValue(for: 12)) font.bodySmall = .system(size: UIFontMetrics.default.scaledValue(for: 11)) var attribution = PlacesMaterialAttribution() attribution.lightModeColor = .black attribution.darkModeColor = .white theme.color = color theme.shape = shape theme.font = font theme.attribution = attribution } else { return PlacesMaterialTheme() } } @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID("ChIJT7FdmYiAhYAROFOvrIxRJDU")) var body: some View { PlaceDetailsCompactView( orientation: .horizontal, query: $query, contentType: [.media(), .address(), .rating(), .type(), .price(), .accessibleEntranceIcon(), .mapsLink(), .directionsLink()], theme: theme, placeDetailsCallback: placeDetailsCallback, preferTruncation: false ) .frame(width: 350) }
自定义地点详情
地点界面套件提供了一种设计系统方法,可大致基于 Material Design(并进行一些 Google 地图专用修改)进行视觉自定义。请参阅 Material Design 的颜色和排版参考文档。默认情况下,此样式遵循 Google 地图的视觉设计语言。

您可以自定义以下样式:
宽度和高度
对于竖屏视图,建议的宽度介于 180 像素到 300 像素之间。对于横向视图,建议的宽度介于 180 像素到 500 像素之间。
最佳做法是不要设置高度。这样,窗口中的内容就可以设置高度,以便显示所有信息。
归因颜色
根据 Google 地图服务条款,您必须使用三种品牌颜色之一来提供 Google 地图提供方标识。进行自定义更改后,此归属信息必须可见且可访问。
我们提供 3 种品牌颜色可供选择,可分别为浅色主题和深色主题设置:
- 浅色主题:
attributionColorLight
,包含白色、灰色和黑色的枚举。 - 深色主题:
attributionColorDark
,包含白色、灰色和黑色的枚举。
自定义示例
此示例展示了如何自定义默认样式属性。
Swift
// Callback for the place details widget. let placeDetailsCallback: (PlaceDetailsResult) -> Void = { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } @Environment(\.colorScheme) var colorScheme var theme: PlacesMaterialTheme { var theme = PlacesMaterialTheme() theme.colorSurface = (colorScheme == .dark ? .blue : .gray) theme.colorOutlineDecorative = (colorScheme == .dark ? .white : .black) theme.colorPrimary = (colorScheme == .dark ? .white : .black) theme.colorOnSurface = (colorScheme == .dark ? .yellow : .red) theme.colorOnSurfaceVariant = (colorScheme == .dark ? .white : .blue) theme.colorOnSecondaryContainer = (colorScheme == .dark ? .white : .red) theme.colorSecondaryContainer = (colorScheme == .dark ? .green : .purple) theme.colorPositive = (colorScheme == .dark ? .yellow : .red) theme.colorNegative = (colorScheme == .dark ? .white : .black) theme.colorInfo = (colorScheme == .dark ? .yellow : .purple) theme.cornerRadius = 10 theme.bodySmall = .system(size: 11) theme.bodyMedium = .system(size: 12) theme.labelLarge = .system(size: 13) theme.headlineMedium = .system(size: 14) theme.attributionColorLightTheme = .black theme.attributionColorDarkTheme = .white return theme } @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID("ChIJT7FdmYiAhYAROFOvrIxRJDU")) var body: some View { PlaceDetailsCompactView( orientation: .vertical, query: $query, contentType: [.media(), .address(), .rating(), .type(), .price(), .accessibleEntranceIcon(), .mapsLink(), .directionsLink()], theme: theme, placeDetailsCallback: placeDetailsCallback, preferTruncation: false ) .frame(width: 350) }