Esta página descreve o utilitário de clustering de marcadores disponível na biblioteca de utilitários SDK do Maps para iOS.
Com o clustering de marcadores, você pode colocar um grande número de marcadores em um mapa sem dificultar a leitura. O utilitário de clustering de marcadores gerenciar vários marcadores em diferentes níveis de zoom.
Quando um usuário vê um mapa com bastante zoom, os marcadores individuais aparecem no mapa. Quando o usuário diminui o zoom, os marcadores se reúnem em clusters, facilitando a visualização.
A captura de tela a seguir mostra o estilo padrão dos clusters de marcadores:
Abaixo está um exemplo de clusters de marcadores personalizados:
Pré-requisitos e observações
Biblioteca de utilitários do SDK do Maps para iOS
O utilitário de clustering de marcadores SDK do Maps para iOS Biblioteca de utilitários Se você ainda não configurou a biblioteca, siga o guia antes de ler o restante desta página.
Para obter o melhor desempenho, o número máximo recomendado de marcadores é 10.000.
Permissão de localização
Este exemplo usa o GPS do dispositivo para localizar o usuário e o mapa nas coordenadas dele. Para ativar
isso, será preciso adicionar uma descrição à permissão NSLocationWhenInUseUsageDescription
no arquivo Info.plist
do projeto.
Para adicionar isso, faça o seguinte:
- Clique no arquivo
Info.plist
no Project Navigator do Xcode para abrir o Editor da lista de propriedades. - Clique no sinal "+" ícone ao lado de "Lista de propriedades da informação" para adicionar uma nova propriedade.
- No campo "key" digite "NSLocationWhenInUseUsageDescription". o Xcode vai automaticamente traduza isso para o nome longo "Privacy - Location When In Use Usage Description". Para um lista completa de possíveis propriedades de permissão de localização, consulte Pedir autorização para os Serviços de localização na documentação do desenvolvedor da Apple.
- Deixe o campo "Tipo" definido como "String".
- Na coluna "Valor", digite uma descrição do motivo pelo qual seu aplicativo exige o uso do local do usuário. Por exemplo, "Localiza o usuário para fornecer listagens de empresas próximas".
Como implementar o clustering de marcadores
A implementação do clustering de marcadores é feita em três etapas:
- Crie uma instância do gerenciador de clusters.
- Transmita os marcadores que você quer agrupar para o gerenciador de clusters.
- Invoque o gerenciador de cluster.
Criando o gerenciador de cluster
Para usar o gerenciador de clusters, faça o seguinte:
- Defina o
ViewController
em que seu mapa é renderizado de acordo com o com o protocoloGMSMapViewDelegate
. - Crie uma instância de
GMUClusterManager
. - Transmita a instância de
GMSMapView
em que você quer implementar o clustering de marcadores em implementações dos seguintes protocolos para a instânciaGMUClusterManager
:GMUClusterIconGenerator
: fornece uma lógica de aplicativo que busca o ícones de cluster para serem usados em diferentes níveis de zoom.GMUClusterAlgorithm
: especifica um algoritmo que determina o comportamento. de como os marcadores são agrupados, como a distância entre os marcadores a serem incluídos no mesmo cluster.GMUClusterRenderer
: fornece a lógica do aplicativo que processa a solicitação real renderização dos ícones de cluster no mapa.
- Defina o delegado do mapa na instância
GMUClusterManager
.
A biblioteca de utilitários inclui implementações padrão do gerador de ícones (GMUDefaultClusterIconGenerator
).
algoritmo (GMUNonHierarchicalDistanceBasedAlgorithm
) e renderizador (GMUDefaultClusterRenderer
).
Também é possível criar seu próprio gerador, algoritmo e renderizador de ícone de exibição personalizado.
O código a seguir cria um gerenciador de cluster usando esses padrões no viewDidLoad
callback de ViewController
:
Swift
import GoogleMaps import GoogleMapsUtils class MarkerClustering: UIViewController, GMSMapViewDelegate { private var mapView: GMSMapView! private var clusterManager: GMUClusterManager! override func viewDidLoad() { super.viewDidLoad() // Set up the cluster manager with the supplied icon generator and // renderer. let iconGenerator = GMUDefaultClusterIconGenerator() let algorithm = GMUNonHierarchicalDistanceBasedAlgorithm() let renderer = GMUDefaultClusterRenderer(mapView: mapView, clusterIconGenerator: iconGenerator) clusterManager = GMUClusterManager(map: mapView, algorithm: algorithm, renderer: renderer) // Register self to listen to GMSMapViewDelegate events. clusterManager.setMapDelegate(self) // ... } // ... }
Objective-C
@import GoogleMaps; @import GoogleMapsUtils; @interface MarkerClustering () <GMSMapViewDelegate> @end @implementation MarkerClustering { GMSMapView *_mapView; GMUClusterManager *_clusterManager; } - (void)viewDidLoad { [super viewDidLoad]; // Set up the cluster manager with a supplied icon generator and renderer. id<GMUClusterAlgorithm> algorithm = [[GMUNonHierarchicalDistanceBasedAlgorithm alloc] init]; id<GMUClusterIconGenerator> iconGenerator = [[GMUDefaultClusterIconGenerator alloc] init]; id<GMUClusterRenderer> renderer = [[GMUDefaultClusterRenderer alloc] initWithMapView:_mapView clusterIconGenerator:iconGenerator]; _clusterManager = [[GMUClusterManager alloc] initWithMap:_mapView algorithm:algorithm renderer:renderer]; // Register self to listen to GMSMapViewDelegate events. [_clusterManager setMapDelegate:self]; // ... } // ... @end
Adicionar marcadores
Há duas maneiras de adicionar marcadores ao clusterer: individualmente ou como uma matriz.
Marcador individual
Swift
let position = CLLocationCoordinate2D(latitude: 47.60, longitude: -122.33) let marker = GMSMarker(position: position) clusterManager.add(marker)
Objective-C
CLLocationCoordinate2D position = CLLocationCoordinate2DMake(47.60, -122.33); GMSMarker *marker = [GMSMarker markerWithPosition:position]; [_clusterManager addItem:marker];
Matriz de marcadores
Swift
let position1 = CLLocationCoordinate2D(latitude: 47.60, longitude: -122.33) let marker1 = GMSMarker(position: position1) let position2 = CLLocationCoordinate2D(latitude: 47.60, longitude: -122.46) let marker2 = GMSMarker(position: position2) let position3 = CLLocationCoordinate2D(latitude: 47.30, longitude: -122.46) let marker3 = GMSMarker(position: position3) let position4 = CLLocationCoordinate2D(latitude: 47.20, longitude: -122.23) let marker4 = GMSMarker(position: position4) let markerArray = [marker1, marker2, marker3, marker4] clusterManager.add(markerArray)
Objective-C
CLLocationCoordinate2D position1 = CLLocationCoordinate2DMake(47.60, -122.33); GMSMarker *marker1 = [GMSMarker markerWithPosition:position1]; CLLocationCoordinate2D position2 = CLLocationCoordinate2DMake(47.60, -122.46); GMSMarker *marker2 = [GMSMarker markerWithPosition:position2]; CLLocationCoordinate2D position3 = CLLocationCoordinate2DMake(47.30, -122.46); GMSMarker *marker3 = [GMSMarker markerWithPosition:position3]; CLLocationCoordinate2D position4 = CLLocationCoordinate2DMake(47.20, -122.23); GMSMarker *marker4 = [GMSMarker markerWithPosition:position4]; NSArray<GMSMarker *> *markerArray = @[marker1, marker2, marker3, marker4]; [_clusterManager addItems:markerArray];
Como invocar o clustering de marcadores
Depois de criar seu clusterer de marcadores e transmitir a ele os marcadores que você quer agrupar, todos
chame o método cluster
na instância do clusterer de marcadores.
Swift
clusterManager.cluster()
Objective-C
[_clusterManager cluster];
Tratamento de eventos em marcadores e grupos
Em geral, ao usar o SDK do Maps para iOS, é necessário implementar para detectar eventos no mapa
GMSMapViewDelegate
protocolo. Você pode ouvir
mapear eventos, mas não é possível
detectam os eventos do gerenciador de clusters com segurança de tipo. Quando o usuário toca em um marcador,
um item de cluster individual ou um cluster, a API aciona
mapView:didTapMarker:
e anexa os dados extras do cluster ao
propriedade marker.userData
. Depois, você pode verificar se o userData
está em conformidade com
O protocolo GMUCluster
para determinar se o usuário tocou em um ícone de cluster ou em um marcador.
Swift
func mapView(_ mapView: GMSMapView, didTap marker: GMSMarker) -> Bool { // center the map on tapped marker mapView.animate(toLocation: marker.position) // check if a cluster icon was tapped if marker.userData is GMUCluster { // zoom in on tapped cluster mapView.animate(toZoom: mapView.camera.zoom + 1) NSLog("Did tap cluster") return true } NSLog("Did tap a normal marker") return false }
Objective-C
- (BOOL)mapView:(GMSMapView *)mapView didTapMarker:(GMSMarker *)marker { // center the map on tapped marker [_mapView animateToLocation:marker.position]; // check if a cluster icon was tapped if ([marker.userData conformsToProtocol:@protocol(GMUCluster)]) { // zoom in on tapped cluster [_mapView animateToZoom:_mapView.camera.zoom + 1]; NSLog(@"Did tap cluster"); return YES; } NSLog(@"Did tap marker in cluster"); return NO; }
O gerenciador de cluster agora intercepta todos os eventos que você implementou
clusterManager
: Os eventos restantes são encaminhados para o mapa.
delegado, se fornecido. Eventos para marcadores padrão
(ou seja, os marcadores não gerados pelo renderizador do cluster) são sempre encaminhados.
ao delegado do mapa.
Personalizar o clustering de marcadores
Você pode fornecer uma implementação personalizada para o
GMUClusterRenderer
, GMUClusterIconGenerator
ou
GMUClusterAlgorithm
É possível basear sua implementação personalizada
sobre os exemplos de implementação desses protocolos incluídos no programa
ou você pode codificar uma implementação totalmente personalizada atendendo à
protocolos.