J'affiche un MKMapView à l'intérieur d'un en-tête de vue de table de parallaxe de style chemin de chemin. Pour créer l'effet, les limites MapView sont plus grandes que la zone visible à l'utilisateur. Je dois définir la région de la carte de manière à ce que toutes les annotations de la carte soient contenues dans le record Visible de MKMAPView. Quelle est la meilleure façon de faire cela? P>
p>
7 Réponses :
Essayez de recevoir de la valeur de vos bords d'annotation (max et min) pour LAN et LON.
Définissez cette valeur au début: p> puis utilisez Cette fonction permet de calculer la portée et la région: p> et utilisez-le dans la mode ViewDidLoad Méthode: P> -(void)viewDidLoad
{
[super viewDidLoad];
[self zoomAndFit];
}
Ce code correspond à toutes les annotations des limites du MapView, mais ce dont j'ai besoin, c'est d'adapter toutes les annotations d'un CGRRECT donné dans les limites du MapView.
@ user2393462435 Ce n'est pas clairement ce que vous essayez exactement de dire ... Lisez-le vous-même et soyez clair dans ce que vous demandez.
@ R.A La taille MAPView est de 320 x 380. Définissez la région de la carte de la carte de manière à ce que toutes les annotations se situent dans la section record (0,0, 20,0, 320.0, 100.0). C'est ça.
Si vous êtes prêt à se rapprocher des calculs, vous pouvez le faire en utilisant une échelle intelligente. P>
Votre zone cible est de 80 grandes sur une carte de 380. Par conséquent, vous voulez une région de 4,75x plus grande que la région calculée pour répondre à vos annotations. (0,25 extra ci-dessus et 3,5 supplémentaires ci-dessous). P>
Tout d'abord, vous devez obtenir une région (ou mapprect, que vous préférez travailler dans) et en faire les mêmes proportions que votre zone visible cibles. En effet, une région très large et courte ne toucherait pas le haut et le bas de la zone visible et de multiplier ainsi sa hauteur ne ferait pas quelque chose qui a touché le haut et le bas de votre vision de carte. Donc, si Avec cela, vous ajoutez ensuite 25% sur le nord de la boîte d'annotations et 350% sur le sud. Vous pouvez le faire en déplaçant le centre 212,5% (de la hauteur actuelle) vers le sud et augmentant la portée verticale de 475%. P>
Maintenant, tout cela est une approximation étant donné que le monde est sphère et que nous ne regardons pas une projection plane (c'est-à-dire 1 degré de latitude près de l'équateur est tiré de plus de 1 degré près des pôles). Mais si vous voulez bien être précis, vous pourriez rechercher les chiffres en fonction de la latitude et de telle. Si vous ne faites que traiter avec des annotations sur une échelle de la taille d'une ville, vous serez probablement bien. P>
espère que cela aide. P> visible_height / visible_width> annotations_height / annotations_width code> Vous devez définir le
annotations_height code> sur
annotations_width * (visible_height / visible_width) p>. P>.
Si vous souhaitez trouver les annotations figurant dans un record donné:
- (void)assureAnnotationViewsAreVisible:(NSArray*)annotations originalRegion:(MKCoordinateRegion)originalRegion { CGFloat smallestX = MAXFLOAT; CGFloat smallestY = MAXFLOAT; CGFloat biggestX = -100; CGFloat biggestY = -100; //NSLog(@"---: %d", annotations.count); for(id<MKAnnotation> *annotation in annotations) { UIView *annotationView = [self.mapView viewForAnnotation:v]; CGRect annotationViewFrame = annotationView.bounds; annotationViewFrame.origin = [self.mapView convertCoordinate:annotationView.coordinate toPointToView:self.mapView]; annotationViewFrame.origin = CGPointMake(annotationViewFrame.origin.x-annotationViewFrame.size.width/2, annotationViewFrame.origin.y-annotationViewFrame.size.height); smallestX = MIN(annotationViewFrame.origin.x, smallestX); smallestY = MIN(annotationViewFrame.origin.y, smallestY); biggestX = MAX(annotationViewFrame.origin.x+annotationViewFrame.size.width, biggestX); biggestY = MAX(annotationViewFrame.origin.y+annotationViewFrame.size.height, biggestY); } //NSLog(@"---"); CGRect bounds = self.mapView.bounds; if(smallestX < bounds.origin.x || smallestY < bounds.origin.y || biggestX > bounds.origin.x+bounds.size.width || biggestY > bounds.origin.y+bounds.size.height) { CGRect neededRect = bounds; neededRect.origin = CGPointMake(MIN(bounds.origin.x, smallestX), MIN(bounds.origin.y, smallestY)); neededRect.size = CGSizeMake(MAX(bounds.size.width, biggestX), MAX(bounds.size.height, biggestY)); MKCoordinateRegion neededRegion = [self.mapView convertRect:neededRect toRegionFromView:self.mapView]; _ignoreRegionChange = YES; [self.mapView setRegion:originalRegion animated:NO]; _ignoreRegionChange = NO; [self.mapView setRegion:neededRegion animated:YES]; } else { MKCoordinateRegion currentRegion = self.mapView.region; _ignoreRegionChange = YES; [self.mapView setRegion:originalRegion animated:NO]; _ignoreRegionChange = NO; [self.mapView setRegion:currentRegion animated:YES]; } }
Où les allonances dans un Nsarray avec les annotations que vous avez (sur la carte ou non)
Quelle est la valeur de maxfloat?
ne sais pas. Il s'agit d'une valeur définie spécifique de plate-forme / d'arche / OS .. Laissez-le dire que c'est ~ 32000
Réglage de la région de la carte afin que toutes les annotations soient contenues dans une certaine partie d'un ci-dessous est un coup d'écran d'un test. La superposition rouge indique le p> p> voici le code. méfiez strong>: c'est tout dans une méthode de simplification de l'ajout à votre code, et il n'est pas testé pour les cas de bord strong> comme passer dans n annotations avec la même coordonnée ou avoir le Annotations si éloignées que la carte devrait être trop zoomée, ou avoir des coordonnées qui s'étendent au bord de la carte à +/- 180 degrés longitude. p> si Vous allez pour un placement parfait (et qui ne le fait pas), voici trois choses à considérer: p> mkmapview code> peut être effectuée en trois étapes. L'entrée est le
mapviev code> et le
annotationsframe code>.
mkmaprect code>
maprect code> contenant toutes les annotations. LI>
MapView.bounds code> et
AnnotationsFrame code>. Li>
-sevissiblemaprect: EdgePadding: Animation: Code> sur la vue Carte. Li>
ol>
p>
AnnotationsFrame CODE>, mais les annotations elles-mêmes peuvent être à l'extérieur. Pour éviter cela, utilisez simplement plus de rembourrage. Par exemple, si vos annotations sont 20x20 et centrées sur la coordonnée, utilisez 10 autres remplissages de tous les côtés. LI>
Partir de iOS 7.0, cela peut être facilement réalisé avec Swift: p> objectif-c: p > montrophanotations code>.
[mapView showAnnotations:mapView.annotations animated:YES];
@ kishan94 utilisez-vous Swift ou Objective-C?
Le code que j'ai écrit avant est pour Swift. J'ai ajouté un exemple de code pour Objective-C, veuillez vérifier.
Ok +1 ajouté, désolé, je n'ai pas essayé à Swift ... @andree
Vous devez d'abord ajouter les annotations: (Bien sûr, cela est après avoir déjà eu une liste d'annotations)
swift4: p> blockQuote>
xxx pré> Vous pouvez utiliser la constante CurrentView ou placer directement le mkmaprect comme tel: ci-dessous: (.VisiblemapRect Retours: P>
"La zone actuellement affichée par le Affichage de la carte. " P>
mapView.annotations(in: mapView.visibleMapRect)
J'ai trouvé un moyen plus facile sans calculer est de laisser la vue Carte le calculer, puis nous ajustons les bords.
//1: Show all annotation on the map view, but without animation self.mapView.showAnnotations(self.mapView.annotations, animated: false) //2: Get the current visible map rect let currentMapRect = self.mapView.visibleMapRect //3: Create the edges inset that you want the map view to show all annotation within let padding = UIEdgeInsets(top: 100, left: 100, bottom: 100, right: 100) //4: Set current map rect but with new padding, also set animation to true to see effect self.mapView.setVisibleMapRect(currentMapRect, edgePadding: padding, animated: true)