С помощью Navigation SDK для iOS можно настраивать удобство использования с картой, определив, какие из встроенных элементов управления пользовательского интерфейса будут отображаться на карте и какие жесты можно использовать. Вы также можете изменить внешний вид интерфейса навигации. Рекомендации по допустимым изменениям интерфейса навигации приведены на странице правил.
Элементы управления пользовательского интерфейса карты
В Navigation SDK предусмотрены встроенные элементы управления, сходные с теми, которые используются в приложении "Google Карты" для iOS. Они отображаются и скрываются с помощью класса GMSUISettings. Изменения, выполненные для этого класса, сразу же отображаются на карте.
Компас
В Navigation SDK предусмотрен значок компаса, который появляется в правом верхнем углу карты при определенных условиях и только если он включен. Когда пользователь нажимает на компас, камера возвращается в положение, при котором направление равно нулю (ориентация по умолчанию), после чего компас скрывается.
Если навигация включена, а режим камеры установлен на "слежение", компас остается видимым, а нажатие на него переключает между наклонным и обзорным режимами камеры.
Чтобы избежать отвлекающих факторов для водителя, компас остается на месте, если заголовок (в режиме портретной съемки) расширяется и конфликтует с положением компаса по умолчанию. Если вы добавите дополнительный элемент управления заголовком или вспомогательное представление заголовка, компас будет скрыт, чтобы избежать конфликтов в интерфейсе.
Компас поддерживает дневной, ночной и тёмный режимы.
Компас включен по умолчанию в версии 11.0.0 и более поздних. Чтобы отключить компас, задайте для свойства compassButton объекта GMSUISettings значение false.
Swift
mapView.settings.compassButton = false
Objective-C
mapView.settings.compassButton = NO;
Кнопка "Мое местоположение"
Кнопка геолокации отображается в правом нижнем углу экрана только, если она включена. При нажатии этой кнопки камера фокусируется на текущем местоположении пользователя, если оно известно. Чтобы включить кнопку, задайте для свойства myLocationButton объекта GMSUISettings значение true.
Swift
mapView.settings.myLocationButton = true
Objective-C
mapView.settings.myLocationButton = YES;
Кнопка центрирования
Если навигация включена, кнопка центрирования появляется, когда пользователь прокручивает карту, и исчезает, когда он нажимает на нее, чтобы центрировать карту. Чтобы кнопка центрирования появилась, задайте для свойства recenterButtonEnabled объекта GMSUISettings значение true. Чтобы кнопка центрирования не появлялась, задайте для recenterButtonEnabled значение false.
Swift
mapView.settings.isRecenterButtonEnabled = true
Objective-C
mapView.settings.recenterButtonEnabled = YES;
Дополнительные элементы интерфейса карты
Navigation SDK предоставляет элементы интерфейса, которые появляются во время навигации, аналогичные тем, которые есть в приложении "Google Карты" для iOS. Вы можете настроить видимость или внешний вид этих элементов управления, как описано в этом разделе. Изменения вступят в силу во время следующей поездки пользователя.
Верхний и нижний колонтитулы навигации

Во время навигации в верхней части экрана появляется заголовок, а в нижней – нижний колонтитул. В заголовке навигации показано название улицы и направление следующего поворота на маршруте, а также направление поворота после него. В нижнем колонтитуле навигации показаны расчетное время и расстояние до пункта назначения, а также расчетное время прибытия.
Вы можете программно включать и отключать видимость верхнего и нижнего колонтитулов навигации, а также задавать их цвета с помощью следующих свойств:
navigationHeaderEnabled– определяет, виден ли заголовок навигации (по умолчаниюtrue).navigationFooterEnabled– определяет, виден ли нижний колонтитул навигации (по умолчаниюtrue).navigationHeaderPrimaryBackgroundColor– задает основной цвет фона для заголовка навигации.navigationHeaderSecondaryBackgroundColor– задает дополнительный цвет фона для заголовка навигации.
В примере кода ниже показано, как включить видимость верхнего и нижнего колонтитулов, а затем задать для navigationHeaderPrimaryBackgroundColor синий цвет, а для navigationHeaderSecondaryBackgroundColor – красный.
Swift
mapView.settings.isNavigationHeaderEnabled = true
mapView.settings.isNavigationFooterEnabled = true
mapView.settings.navigationHeaderPrimaryBackgroundColor = .blue
mapView.settings.navigationHeaderSecondaryBackgroundColor = .red
Objective-C
mapView.settings.navigationHeaderEnabled = YES;
mapView.settings.navigationFooterEnabled = YES;
mapView.settings.navigationHeaderPrimaryBackgroundColor = [UIColor blueColor];
mapView.settings.navigationHeaderSecondaryBackgroundColor = [UIColor redColor];
Заголовок дополнительного элемента навигации
Вы можете настроить приложение, заменив заголовок дополнительной навигации на собственное представление. Для этого нужно создать представление, реализующее протокол GMSNavigationAccessoryView. В этом протоколе есть один обязательный метод: -heightForAccessoryViewConstrainedToSize:onMapView:. Вам предоставляется максимально доступный размер для вашего представления в заданном mapView, и вы должны указать высоту, которая требуется для вашего представления.
Затем вы можете передать это представление в mapView, вызвав setHeaderAccessoryView:. mapView анимирует все текущие представления, а затем анимирует ваше пользовательское представление. Чтобы отображался пользовательский вид, заголовок навигации должен быть видимым.
Чтобы удалить специальный заголовок, передайте nil в setHeaderAccessoryView:.
Если размер представления должен измениться, вызовите метод invalidateLayoutForAccessoryView:, передав в него представление, размер которого нужно изменить.
Пример
В примере кода ниже показано специальное представление, в котором реализован протокол GMSNavigationAccessoryView. Затем это представление используется для настройки дополнительного представления заголовка навигации.
Swift
class MyCustomView: UIView, GMSNavigationAccessoryView {
…
func heightForAccessoryViewConstrained(to size: CGSize, on mapView: GMSMapView) -> CGFloat {
// viewHeight gets calculated as the height your view needs.
return viewHeight
}
…
}
let customView = MyCustomView(...)
mapView.setHeaderAccessory(customView)
// At some later point customView changes size.
mapView.invalidateLayout(forAccessoryView: customView)
// Remove the custom header accessory view.
mapView.setHeaderAccessory(nil)
Objective-C
@interface MyCustomView : UIView <GMSNavigationAccessoryView>
…
@end
@implementation MyCustomView
…
- (CGFloat)heightForAccessoryViewConstrainedToSize:(CGSize)size onMapView:(GMSMapView *)mapView {
// viewHeight gets calculated as the height your view needs.
return viewHeight;
}
…
@end
MyCustomView *customView = [[MyCustomView alloc] init…];
[_mapView setHeaderAccessoryView:customView];
// At some later point customView changes size.
[_mapView invalidateLayoutForAccessoryView:customView];
// Remove the custom header accessory view.
[_mapView setHeaderAccessoryView:nil];
Цвета заголовка в режиме низкой освещенности
Navigation SDK для iOS рассчитывает рекомендуемый режим освещения на основе времени суток и текущего местоположения устройства и вызывает метод прослушивателя GMSNavigatorListener.didChangeSuggestedLightingMode при изменении рекомендуемого режима (например, на рассвете или закате).
Вы можете программно изменить поведение режима низкой освещенности следующими способами:
- Чтобы управлять переключением между обычным режимом и режимом низкой освещенности, задайте для свойства
GMSMapView.lightingModeзначениеGMSNavigationLightingMode. Подробнее о том, как настроить автоматическое переключение между режимами… - Настройте основной и дополнительный цвета фона заголовка навигации в режиме низкой освещенности, задав свойства
navigationHeaderPrimaryBackgroundColorNightModeиnavigationHeaderSecondaryBackgroundColorNightModeдля объектаGMSUISettings.
Список маршрутов
Вы можете предоставить пошаговые инструкции в своем приложении. В следующем примере показан один из возможных способов сделать это. В зависимости от реализации эти шаги могут различаться.
- Включите кнопку точки входа после того, как
setDestinationsвGMSNavigator(навигаторе) успешно завершится иguidanceActiveв навигаторе будет включен. - Когда пользователь нажимает кнопку точки входа, создайте
GMSNavigationDirectionsListController(контроллер) с навигатором, связанным сGMSMapView(mapView). - Добавьте контроллер в экземпляр
UIViewController(контроллер представления), аdirectionsListView– в качестве подпредставления контроллера представления. МетодыreloadDataиinvalidateLayoutв контроллере должны вызываться так же, как и в случае сUICollectionView. - Добавьте контроллер представления в иерархию контроллеров представлений приложения.
В примере ниже показано, как добавить DirectionsListViewController.
Swift
override func viewDidLoad() {
super.viewDidLoad()
// Add the directionsListView to the host view controller's view.
let directionsListView = directionsListController.directionsListView
directionsListView.frame = self.view.frame
self.view.addSubview(directionsListView)
directionsListView.translatesAutoresizingMaskIntoConstraints = false
directionsListView.topAnchor.constraint(equalTo: self.view.topAnchor).isActive = true
directionsListView.leadingAnchor.constraint(equalTo: self.view.leadingAnchor).isActive = true
directionsListView.trailingAnchor.constraint(equalTo: self.view.trailingAnchor).isActive = true
directionsListView.bottomAnchor.constraint(equalTo: self.view.bottomAnchor).isActive = true
...
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
// Make sure data is fresh when the view appears.
directionsListController.reloadData()
...
}
override func willTransition(to newCollection: UITraitCollection, with coordinator: UIViewControllerTransitionCoordinator) {
super.willTransition(to: newCollection, with: coordinator)
// Invalidate the layout during rotation.
coordinator.animate(alongsideTransition: {_ in
self.directionsListController.invalidateLayout()
})
...
}
Objective-C
- (void)viewDidLoad {
[super viewDidLoad];
// Add the directionsListView to the host view controller's view.
UIView *directionsListView = _directionsListController.directionsListView;
directionsListView.frame = self.view.bounds;
[self.view addSubview:directionsListView];
directionsListView.translatesAutoresizingMaskIntoConstraints = NO;
[directionsListView.topAnchor constraintEqualToAnchor:self.view.topAnchor].active = YES;
[directionsListView.leadingAnchor constraintEqualToAnchor:self.view.leadingAnchor].active = YES;
[directionsListView.trailingAnchor constraintEqualToAnchor:self.view.trailingAnchor].active = YES;
[directionsListView.bottomAnchor constraintEqualToAnchor:self.view.bottomAnchor].active = YES;
...
}
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
// Make sure data is fresh when the view appears.
[_directionsListController reloadData];
...
}
- (void)willTransitionToTraitCollection:(UITraitCollection *)newCollection
withTransitionCoordinator:(id<UIViewControllerTransitionCoordinator>)coordinator {
[super willTransitionToTraitCollection:newCollection withTransitionCoordinator:coordinator];
void(^animationBlock)(id <UIViewControllerTransitionCoordinatorContext>context) =
^void(id <UIViewControllerTransitionCoordinatorContext>context) {
[_directionsListController invalidateLayout];
};
// Invalidate the layout during rotation.
[coordinator animateAlongsideTransition:animationBlock
completion:nil];
...
}
...
Индикатор выполнения поездки

Индикатор выполнения поездки – это вертикальная полоса, которая появляется в начале карты при запуске навигации. Если он включен, то на экране показывается обзор всего маршрута, а также пункт назначения и текущее местоположение пользователя.
Это позволяет пользователям заранее узнавать о возможных проблемах, например пробках, не увеличивая масштаб. При необходимости они могут изменить маршрут. Если пользователь меняет маршрут, индикатор выполнения сбрасывается, как если бы поездка началась заново.
На индикаторе выполнения поездки отображаются следующие статусы:
Статус трафика – статус трафика на предстоящем участке маршрута.
Текущее местоположение – текущее местоположение водителя в поездке.
Пройденный маршрут – пройденная часть поездки.
Включите индикатор выполнения поездки, задав свойство navigationTripProgressBarEnabled в GMSUISettings.
Swift
mapView.settings.isNavigationTripProgressBarEnabled = true
Objective-C
mapView.settings.navigationTripProgressBarEnabled = YES;
Расположение индикатора выполнения поездки
- Левая сторона панели примерно совпадает с левой стороной спидометра, логотипа Google и кнопки "Вернуть в центр" (когда она видна). Ширина – 12 пт.
- Индикатор выполнения поездки динамически реагирует на вертикальное пространство на экране. Нижний край панели находится на расстоянии 210 пт от нижнего края экрана. Верхняя часть индикатора выполнения поездки находится на расстоянии не менее 170 пт от верхней части экрана, а максимальная высота индикатора составляет 400 пт.
- Если индикатор выполнения поездки перекрывает заголовок навигации или другие элементы интерфейса навигации, он отображается под ними.
Prompt Visibility API (экспериментальная функция)
Prompt Visibility API позволяет избежать конфликтов между элементами интерфейса, созданными Navigation SDK, и вашими собственными элементами интерфейса. Для этого нужно добавить прослушиватель, который будет получать обратный вызов перед появлением элемента интерфейса Navigation SDK и сразу после его удаления. Дополнительную информацию, в том числе примеры кода, можно найти в разделе Prompt Visibility API на странице Настройка уведомлений о сбоях в реальном времени.
Управление спидометром
Если навигация включена и выбран режим поездки на автомобиле, Navigation SDK для iOS показывает в нижнем углу карты элемент управления с текущим ограничением скорости. Если водитель превышает ограничение скорости, элемент управления разворачивается и показывает второй спидометр с текущей скоростью.
Вы можете настроить уровни предупреждений, чтобы изменить форматирование спидометра, когда водитель превышает ограничение скорости на определенную величину. Например, можно указать, что текущая скорость должна отображаться красным цветом, если водитель превышает ограничение на 5 миль/ч, и на красном фоне, если превышение составляет 10 миль/ч.
Чтобы показать элемент управления ограничением скорости, задайте для свойства shouldDisplaySpeedometer объекта GMSUISettings значение true. Чтобы отключить показ элемента управления ограничением скорости, задайте для shouldDisplaySpeedometer значение false.
Swift
mapView.settings.shouldDisplaySpeedometer = true
Objective-C
mapView.settings.shouldDisplaySpeedometer = YES;
Подробнее о том, как настроить оповещения спидометра…
Маркеры пунктов назначения
Вы можете показать или скрыть маркеры пунктов назначения для заданного маршрута, установив свойство showsDestinationMarkers объекта GMSUISettings. В примере ниже показано, как отключить маркеры пунктов назначения.
Swift
mapView.settings.showsDestinationMarkers = false
Objective-C
mapView.settings.showsDestinationMarkers = NO;
Функции карт
Navigation SDK позволяет дополнительно настраивать навигацию для пользователей. Изменения, которые вы вносите в экземпляр, отражаются при следующем обновлении приложения пользователем.
Выделение пункта назначения и входов
Если пункт назначения создан с помощью placeID, здание будет выделено и по возможности будет показан значок входа. Эти визуальные подсказки помогают пользователям различать и переходить к нужному месту назначения.
Чтобы создать целевую страницу с помощью placeID, используйте один из инициализаторов GMSNavigationWaypoint, который принимает placeID. Например, пункты назначения, созданные в руководстве по навигации по маршруту, включают выделение пункта назначения и метки входа, если они доступны.
Показ 3D-зданий во время навигации
По умолчанию 3D-здания показываются в режиме навигации. Чтобы отключить эту функцию, задайте для параметра buildingsEnabled значение false (Swift) или NO (Objective-C).
Отключение жестов по умолчанию
Вы можете отключить жесты по умолчанию на карте, задав свойства класса GMSUISettings, который доступен как свойство GMSMapView.
Ниже перечислены жесты, которые можно включить и отключить программным способом. Обратите внимание, что отключение жеста не ограничивает программный доступ к настройкам камеры.
scrollGestures– определяет, включены ли жесты прокрутки. Если этот параметр включен, пользователи могут перемещать камеру, проводя пальцем по экрану.zoomGestures– определяет, включены ли жесты масштабирования. Если этот параметр включен, пользователи могут дважды нажать на экран, нажать на него двумя пальцами или свести пальцы, чтобы изменить масштаб камеры. Обратите внимание, что двойное нажатие или сведение пальцев при включенныхscrollGesturesможет привести к панорамированию камеры в указанную точку.tiltGestures– определяет, включены ли жесты наклона. Если эта функция включена, пользователи могут наклонять камеру, проводя по экрану двумя пальцами вверх или вниз.rotateGestures– определяет, включены ли жесты вращения. Если этот параметр включен, пользователи могут поворачивать камеру, вращая карту двумя пальцами.
В этом примере отключены жесты панорамирования и масштабирования.
Swift
mapView.settings.scrollGestures = false
mapView.settings.zoomGestures = false
Objective-C
mapView.settings.scrollGestures = NO;
mapView.settings.zoomGestures = NO;
Элементы управления и интерфейса
Вы можете размещать элементы управления и другие элементы интерфейса относительно верхнего и нижнего колонтитулов навигации, используя следующие свойства:
navigationHeaderLayoutGuidenavigationFooterLayoutGuidebottomTrailingButtonsLayoutGuide
В следующем примере кода показано, как использовать направляющие макета для размещения пары меток в режиме просмотра карты.
Swift
/* Add a label to the top left, positioned below the header. */
let topLabel = UILabel()
topLabel.text = "Top Left"
mapView.addSubview(topLabel)
topLabel.translatesAutoresizingMaskIntoConstraints = false
topLabel.topAnchor.constraint(equalTo: mapView.navigationHeaderLayoutGuide.bottomAnchor).isActive = true
topLabel.leadingAnchor.constraint(equalTo: mapView.leadingAnchor).isActive = true
/* Add a label to the bottom right, positioned above the footer. */
let bottomLabel = UILabel()
bottomLabel.text = "Bottom Right"
mapView.addSubview(bottomLabel)
bottomLabel.translatesAutoresizingMaskIntoConstraints = false
bottomLabel.bottomAnchor.constraint(equalTo: mapView.navigationFooterLayoutGuide.topAnchor).isActive = true
bottomLabel.trailingAnchor.constraint(equalTo: mapView.trailingAnchor).isActive = true
Objective-C
/* Add a label to the top left, positioned below the header. */
UILabel *topLabel = [[UILabel alloc] init];
topLabel.text = @"Top Left";
[view addSubview:topLabel];
topLabel.translatesAutoresizingMaskIntoConstraints = NO;
[topLabel.topAnchor
constraintEqualToAnchor:mapView.navigationHeaderLayoutGuide.bottomAnchor].active = YES;
[topLabel.leadingAnchor constraintEqualToAnchor:mapView.leadingAnchor].active = YES;
/* Add a label to the bottom right, positioned above the footer. */
UILabel *bottomLabel = [[UILabel alloc] init];
bottomLabel.text = @"Bottom Right";
[view addSubview:bottomLabel];
bottomLabel.translatesAutoresizingMaskIntoConstraints = NO;
[bottomLabel.bottomAnchor
constraintEqualToAnchor:mapView.navigationFooterLayoutGuide.topAnchor].active = YES;
[bottomLabel.trailingAnchor constraintEqualToAnchor:mapView.trailingAnchor].active = YES;
Пример использования bottomTrailingButtonsLayoutGuide для размещения кнопки сообщения о помехах в реальном времени приведен в разделе Настройка сообщений о помехах в реальном времени.
Скрыть альтернативные маршруты
Если пользовательский интерфейс перегружен информацией, вы можете уменьшить ее объем, показывая меньше альтернативных маршрутов, чем по умолчанию (два), или не показывая их вообще. Вы можете настроить этот параметр перед получением маршрутов, настроив GMSNavigationRoutingOptions и задав для alternateRoutesStrategy одно из следующих перечисляемых значений:
| Перечисляемое значение | Описание |
|---|---|
| GMSNavigationAlternateRoutesStrategyAll | По умолчанию. Показывает до двух альтернативных маршрутов. |
| GMSNavigationAlternateRoutesStrategyOne | Показывает один альтернативный маршрут (если он доступен). |
| GMSNavigationAlternateRoutesStrategyNone | Скрывает альтернативные маршруты. |
Пример
В следующем примере кода показано, как полностью скрыть альтернативные маршруты.
Swift
let routingOptions = GMSNavigationRoutingOptions(alternateRoutesStrategy: .none)
navigator?.setDestinations(destinations,
routingOptions: routingOptions) { routeStatus in
...
}
Objective-C
GMSNavigationRoutingOptions *routingOptions = [[GMSNavigationRoutingOptions alloc] initWithAlternateRoutesStrategy:GMSNavigationAlternateRoutesStrategyNone];
[navigator setDestinations:destinations
routingOptions:routingOptions
callback:^(GMSRouteStatus routeStatus){...}];