Composant Advanced Place Details
La version avancée du composant Place Details offre les mêmes fonctionnalités que Places Details Essentials. Il vous permet également de choisir d'afficher ou non le nom du lieu, de configurer les boutons d'action du composant et d'appliquer des options de recherche et de filtrage aux avis et aux contenus multimédias affichés.
Configuration avancée des détails du lieu
Utilisez AdvancedPlaceDetailsView ou AdvancedPlaceDetailsCompactView pour accéder aux fonctionnalités avancées.
Options d'affichage du contenu
Vous pouvez spécifier le contenu à afficher à l'aide des énumérations dans AdvancedPlaceDetailsContent. Vous pouvez configurer le même contenu que Places Details Essentials et choisir d'afficher ou non le nom du lieu.
Configurer les boutons d'action
Utilisez les méthodes .cornerActions et .mainActions de AdvancedPlaceDetailsView ou AdvancedPlaceDetailsCompactView pour supprimer ou personnaliser les boutons d'action.
Exigences concernant l'attribution visuelle
Important : Vous devez indiquer clairement aux utilisateurs finaux quand un bouton d'action personnalisée partagera des informations utilisateur avec un tiers autre que Google. Consultez les exigences concernant l'attribution visuelle.
L'exemple de droite montre une image personnalisée qui indique clairement que les informations utilisateur seront envoyées à "Altostrat".
Appliquer des options de recherche et de filtrage
Utilisez les méthodes .searchMediaOptions et .searchReviewOptions de AdvancedPlaceDetailsView ou AdvancedPlaceDetailsCompactView pour activer la recherche et le filtrage des contenus multimédias ou des avis.
Créer des emplacements de contenu personnalisés
Les emplacements de contenu personnalisés vous permettent d'ajouter votre propre contenu (comme des résumés générés par l'IA, des codes temporels d'itinéraires ou des badges personnalisés) directement dans des zones de mise en page prédéfinies.
Pour ajouter des contenus personnalisés, utilisez la méthode .placeDetailsCompactContentSlot de AdvancedPlaceDetailsCompactView. Les positions disponibles sont .basicSectionTop et .basicSectionBottom.
Exigences d'attribution et suggestions de contenu pour les emplacements de contenu
Lorsqu'un emplacement de contenu personnalisé est monté, la clause de non-responsabilité est automatiquement mise à jour pour préciser quel contenu est fourni par Google et quel contenu est fourni par des tiers.
À faire
Maintenez une hiérarchie visuelle claire entre les détails des établissements Google et le contenu personnalisé pour éviter toute ambiguïté sur la source des informations.
À faire
Pensez à des insights localisés à forte valeur ajoutée, adaptés aux objectifs immédiats de vos utilisateurs. Les contenus personnalisés, tels que les créneaux de réservation en temps réel ou la disponibilité actuelle, aident les utilisateurs à prendre des décisions plus rapidement et de manière plus éclairée.
À éviter
Ne dupliquez pas les informations existantes sur les établissements Google, comme les notes, les avis ou les horaires d'ouverture, même si vous avez masqué le contenu fourni par Google. Cela peut dérouter les utilisateurs quant à la source du contenu et à son origine (Google ou un tiers).
À éviter
N'affichez pas d'affirmations ou de badges non attribués (par exemple, "Recommandation n° 1 !") qui pourraient être confondus avec des mentions officielles de Google. Le contenu personnalisé doit indiquer explicitement sa source.
À éviter
N'incluez pas d'annonces, de textes marketing, de remises promotionnelles ni d'invites à s'abonner dans les conteneurs d'emplacements personnalisés.
Exemples avancés de Place Details
Omettre le nom du lieu
Pour omettre le nom du lieu, n'incluez pas.name dans le paramètre content de AdvancedPlaceDetailsConfiguration.
Swift
struct DemoView: View { static let peetsCoffeePlaceID = "ChIJT7FdmYiAhYAROFOvrIxRJDU" // Query for loading the place details component. @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID(peetsCoffeePlaceID) ) @State private var favoritePlaces: Set<String> = [] var body: some View { AdvancedPlaceDetailsView( query: $query, configuration: AdvancedPlaceDetailsConfiguration( content:[.address()], theme: PlacesMaterialTheme() ), placeDetailsCallback: { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } ) } }
Supprimer les boutons d'action
Swift
struct DemoView: View { static let peetsCoffeePlaceID = "ChIJT7FdmYiAhYAROFOvrIxRJDU" @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID(peetsCoffeePlaceID) ) var body: some View { AdvancedPlaceDetailsView( query: $query, configuration: AdvancedPlaceDetailsConfiguration( content: AdvancedPlaceDetailsView.allContent, theme: PlacesMaterialTheme() ), placeDetailsCallback: { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } ) .mainActions{ _ in return [] } } }
Ajouter des actions personnalisées et prédéfinies
Cet exemple ajoute une option permettant à un utilisateur de marquer un lieu comme favori ou de le supprimer de ses favoris, ainsi que l'action prédéfinie Ouvrir dans Maps.
Swift
struct DemoView: View { static let peetsCoffeePlaceID = "ChIJT7FdmYiAhYAROFOvrIxRJDU" @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID(peetsCoffeePlaceID) ) @State var favoritePlaces: Set<String> = [] var body: some View { AdvancedPlaceDetailsView( query: $query, configuration: AdvancedPlaceDetailsConfiguration( content: AdvancedPlaceDetailsView.allContent, theme: PlacesMaterialTheme() ), placeDetailsCallback: { result in if let place = result.place { print("Place: \(place.description)") } else { print("Error: \(String(describing: result.error))") } } ) .mainActions{ place in var actions: [MainPlaceActionElement] = [] let placeID = place.placeID! if self.favoritePlaces.contains(placeID) { actions.append( .action( MainPlaceAction( image: Image(systemName: "heart.fill"), label: "Unfavorite" ) { _ in self.toggleFavorite(placeID) } ) ) } else { actions.append( .action( MainPlaceAction( image: Image(systemName: "heart"), label: "Favorite" ) { _ in self.toggleFavorite(placeID) } ) ) } actions.append(.actionId(.openMap(style: .primary))) return actions } .cornerActions { place in var actions: [CornerPlaceActionElement] = [] let placeID = place.placeID! if self.favoritePlaces.contains(placeID) { actions.append( .action( CornerPlaceAction( image: Image(systemName: "heart.fill"), accessibilityLabel: "Unfavorite", ) { _ in self.toggleFavorite(placeID) } ) ) } else { actions.append( .action( CornerPlaceAction( image: Image(systemName: "heart"), accessibilityLabel: "Favorite", ) { _ in self.toggleFavorite(placeID) } ) ) } actions.append(.actionId(.openMap(style: .primary))) return actions } } func toggleFavorite(_ placeID: String) { if favoritePlaces.contains(placeID) { favoritePlaces.remove(placeID) } else { favoritePlaces.insert(placeID) } } }
Filtrer les avis et les contenus multimédias
Cet exemple de code n'affiche que les contenus multimédias et les avis mentionnant le mot "café".
Swift
struct DemoView: View { static let peetsCoffeePlaceID = "ChIJT7FdmYiAhYAROFOvrIxRJDU" @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID(peetsCoffeePlaceID) ) let searchMediaOptions = SearchMediaOptions(query: "coffee") let searchReviewsOptions = SearchReviewsOptions(query: "coffee") var body: some View { AdvancedPlaceDetailsView( query: $query, configuration: AdvancedPlaceDetailsConfiguration( content: [.media(), .reviews()], theme: PlacesMaterialTheme() ), placeDetailsCallback: { _ in } ) .searchMediaOptions(searchMediaOptions) { results in guard let result = results.first else { return } switch result { case .success(let summary): print("Summary: \(summary)") case .failure(let error): print("Error: \(error)") } } .searchReviewsOptions(searchReviewsOptions) { results in guard let result = results.first else { return } switch result { case .success(let summary): print("Summary: \(summary)") case .failure(let error): print("Error: \(error)") } } } }
Créer des emplacements de contenu
Cet exemple ajoute du contenu aux emplacements basicSectionTop et basicSectionBottom.
Swift
import SwiftUI import PlacesSwift struct ItineraryCard: View { static let peetsCoffeePlaceID = "ChIJT7FdmYiAhYAROFOvrIxRJDU" @State var query: PlaceDetailsQuery = PlaceDetailsQuery( identifier: .placeID(peetsCoffeePlaceID) ) var body: some View { AdvancedPlaceDetailsCompactView( orientation: .vertical, query: $query, configuration: AdvancedPlaceDetailsCompactConfiguration( content: AdvancedPlaceDetailsCompactView.allContent, theme: PlacesMaterialTheme() ), placeDetailsCallback: { _ in } ) .placeDetailsCompactContentSlot(position: .basicSectionTop) { place in Text("Day 2 • 2:30 PM") .font(.caption) .fontWeight(.bold) .foregroundColor(.accentColor) } .placeDetailsCompactContentSlot(position: .basicSectionBottom) { place in VStack(alignment: .leading, spacing: 4) { Text("AI Notes") .font(.caption) .bold() Text("Great quiet atmosphere for morning meetings. Famous for house-roasted pour-overs.") .font(.footnote) .foregroundColor(.secondary) } .padding(8) .background(Color(.systemGray6)) .cornerRadius(8) } } }