# Place Search component


The Place Search component of the Places UI Kit renders the results of a place search in a list.
![Places UI Kit Place Search component](https://developers.google.com/static/maps/documentation/places/images/place-search-hero.jpg)


You can customize the Place Search list. You can specify:

- The content to display
- Media size in vertical orientation
- Text truncation
- The orientation
- Theme overrides that match your brand and app's design language
- The position of the attribution
- Whether a place is selectable


You can also customize the request to perform either a [`SearchByTextRequest`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/SearchByTextRequest.md.txt) or a [`SearchNearbyRequest`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/SearchNearbyRequest.md.txt).

> [!TIP]
> The [Advanced version of the Place Search component](https://developers.google.com/maps/documentation/places/ios-sdk/advanced-place-search-ui-kit.md.txt) offers the same features as the Place Search component and also allows developers to configure the action buttons of the component and apply search and filtering options to the reviews and media that are displayed.

## Billing


You are billed each time the `SearchByTextRequest()` or `PlaceSearchViewRequest()` binding value is changed.

## Add Place Search to your app

> [!TIP]
> **Tip:** [See the complete example](https://developers.google.com/maps/documentation/places/ios-sdk/place-search-ui-kit.md.txt#examples).


Add the Place Search widget using the `PlaceSearchView class`.

### Swift

```swift
PlaceSearchView(
      orientation: .horizontal, // default is vertical
      request: $placeSearchViewRequest,
      configuration: configuration
)
```


When you want your app to load a text search or nearby search result, update your `PlaceSearchViewRequest` value.

### Swift

```swift
// use placeSearchViewRequest = .searchNearby(...) to  configure a searchNearby request

  @State private var let placeSearchViewRequest = .searchByText(
    SearchByTextRequest(
      textQuery: "Googleplex",
      placeProperties: [.all],
      locationBias: CircularCoordinateRegion(
        center: CLLocationCoordinate2D(latitude: 0, longitude: 0),
        radius: 0
      )
    )
  )
    
```


You can also optionally receive callbacks when the component loads, a place is selected, or when there is an error loading the component.

### Swift

```swift
.onLoad { places in
  print("places: \(places)")
}
.onRequestError { error in
  print("error: \(error)")
}
.onPlaceSelected { place in
  print("place: \(place)")
}
    
```

## Customize the Place Search component

### Customize content

You must specify which content your component will display.

> [!NOTE]
> **Note:** The Place name will always appear.


This example configures the component to display the address and rating of the Place.

### Swift

```swift
private let configuration = PlaceSearchConfiguration(
    content: [.address(), .rating()]
)
```


You can also optionally customize the following aspects of the content that appears in your Place Search component:

- [`content`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Enums/PlaceSearchContent.md.txt): The content shown in the component.
- [`mediaSize`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Enums/PlaceSearchContent.md.txt#mediasize:): The photo size in the vertical orientation of the fragment. The default is small. Specified in content.
- [`preferTruncation`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlaceSearchConfiguration.md.txt#prefertruncation): Whether to truncate text of each Place Details view. The default is false.
- [`theme`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlaceSearchConfiguration.md.txt#theme): Your custom theme that inherits from PlacesMaterialTheme. Learn more about theming.
- [`attributionPosition`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlaceSearchConfiguration.md.txt#attributionposition): Whether to show the Google Maps attribution at the top or bottom of the component. The default is .top.
- [`selectable`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlaceSearchConfiguration.md.txt#selectable): Whether each place in the list is selectable. If it is selectable, `onPlaceSelected` closure will be called after a place is selected. The default is false.


Add your customization configuration to [`PlaceSearchConfiguration`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlaceSearchConfiguration.md.txt).

### Swift

```swift
private let configuration = PlaceSearchConfiguration(
    content: [.address, .rating, .media(size: .large)],
    preferTruncation: true, // default is false
    theme: PlacesMaterialTheme(),
    attributionPosition: .bottom, // default is top
    selectable: true // default is false
)
        
```

### Customize orientation


The default orientation is vertical. You can specify a horizontal orientation in `PlaceSearchView`.

### Swift

```swift
PlaceSearchView(
      orientation: .horizontal, // default is vertical
      request: $placeSearchViewRequest,
      configuration: configuration
)
        
```

### Customize the theme


You can specify a theme that overrides any of the default style attributes. The default is [`PlacesMaterialTheme`](https://developers.google.com/maps/documentation/places/ios-sdk/reference/swift/Structs/PlacesMaterialTheme.md.txt).


See the [Custom styling](https://developers.google.com/maps/documentation/places/ios-sdk/places-ui-kit-custom-styling.md.txt) section for more information on theming.


The Places UI Kit provides a dark theme by default, so you may need to customize both dark and light themes. To customize the dark theme, add values for `.dark` and `attribution.darkModeColor` to your [custom theme](https://developers.google.com/maps/documentation/places/ios-sdk/place-search-ui-kit.md.txt#customize-the-theme_1).

## Examples

### Add the Place Search component

### Swift

```swift
struct PlaceSearchDemoView: View {
  private let configuration = PlaceSearchConfiguration(
    content: [.address(), .rating(), .type(), .media(size: .large)],
    preferTruncation: true,  // default is false
    theme: PlacesMaterialTheme(),
    attributionPosition: .bottom,  // default is top
    selectable: true  // default is false
  )
  // can also do let placeSearchViewRequest = .searchNearby(...) to  configure a searchNearby request
  @State private var placeSearchViewRequest: PlaceSearchViewRequest = .searchByText(
    SearchByTextRequest(
      textQuery: "Googleplex",
      placeProperties: [.all],
      locationBias: CircularCoordinateRegion(
        center: CLLocationCoordinate2D(latitude: 0, longitude: 0),
        radius: 0
      )
    )
  )
  var body: some View {
    PlaceSearchView(
      orientation: .horizontal,  // default is vertical
      request: $placeSearchViewRequest,
      configuration: configuration
    )
    .onLoad { places in
      print("places: \(places)")
    }
    .onRequestError { error in
      print("error: \(error)")
    }
    .onPlaceSelected { place in
      print("place: \(place)")
    }
  }
}
    
```

### Customize the theme


The Places UI Kit provides a dark theme by default, so you may need to customize both dark and light themes. To customize the dark theme, add values for `.dark` and `attribution.darkModeColor` to your custom theme.

### Swift

```swift
@Environment(\.colorScheme) var colorScheme
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()
    }
}
        
```