2010-10-29 78 views
0

我正在尋找一些幫助完成基於當前位置註釋和我設置的註釋在MKMapView上設置區域的一些代碼。將MKMapView區域設置爲以兩個註釋爲中心

我想計算兩者之間的距離並設置兩者之間的中心,然後縮小以便兩者都可以看到。它似乎在我的模擬器中工作正常,但不幸的是userLocation.coordinate固定到Apple總部。當我在設備上測試時,我看到了奇怪的行爲。如果兩個註釋在相同的緯度上有些水平,通常會縮小並設置合適的區域,但如果垂直距離較大,則不會正確縮小。

我用代碼中發現here,和編輯一點點適合我的需要:

是困惑我
CLLocationCoordinate2D southWest = mapView.userLocation.coordinate; 
CLLocationCoordinate2D northEast = southWest; 

southWest.latitude = MIN(southWest.latitude, annotation.coordinate.latitude); 
southWest.longitude = MIN(southWest.longitude, annotation.coordinate.longitude); 

northEast.latitude = MAX(northEast.latitude, annotation.coordinate.latitude); 
northEast.longitude = MAX(northEast.longitude, annotation.coordinate.longitude); 

CLLocation *locSouthWest = [[CLLocation alloc] initWithLatitude:southWest.latitude longitude:southWest.longitude]; 
CLLocation *locNorthEast = [[CLLocation alloc] initWithLatitude:northEast.latitude longitude:northEast.longitude]; 

// This is a diag distance (if you wanted tighter you could do NE-NW or NE-SE) 
CLLocationDistance meters = [locSouthWest distanceFromLocation:locNorthEast]; 

MKCoordinateRegion region; 
region.center.latitude = (southWest.latitude + northEast.latitude)/2.0; 
region.center.longitude = (southWest.longitude + northEast.longitude)/2.0; 
region.span.latitudeDelta = meters/111319.5; 
region.span.longitudeDelta = 0.0; 

MKCoordinateRegion savedRegion = [mapView regionThatFits:region]; 
[mapView setRegion:savedRegion animated:YES]; 

[locSouthWest release]; 
[locNorthEast release]; 

一件事是,他說:northEast = southWest ......

在此先感謝誰誰得到了一些幫助,輸入:)

回答

-1

這個博客中可以爲您提供洞察力,需要

http://codisllc.com/blog/zoom-mkmapview-to-fit-annotations/

-(void)zoomToFitMapAnnotations:(MKMapView*)mapView 
{ 
    if([mapView.annotations count] == 0) 
     return; 

    CLLocationCoordinate2D topLeftCoord; 
    topLeftCoord.latitude = -90; 
    topLeftCoord.longitude = 180; 

    CLLocationCoordinate2D bottomRightCoord; 
    bottomRightCoord.latitude = 90; 
    bottomRightCoord.longitude = -180; 

    for(MapAnnotation* annotation in mapView.annotations) 
    { 
     topLeftCoord.longitude = fmin(topLeftCoord.longitude, annotation.coordinate.longitude); 
     topLeftCoord.latitude = fmax(topLeftCoord.latitude, annotation.coordinate.latitude); 

     bottomRightCoord.longitude = fmax(bottomRightCoord.longitude, annotation.coordinate.longitude); 
     bottomRightCoord.latitude = fmin(bottomRightCoord.latitude, annotation.coordinate.latitude); 
    } 

    MKCoordinateRegion region; 
    region.center.latitude = topLeftCoord.latitude - (topLeftCoord.latitude - bottomRightCoord.latitude) * 0.5; 
    region.center.longitude = topLeftCoord.longitude + (bottomRightCoord.longitude - topLeftCoord.longitude) * 0.5; 
    region.span.latitudeDelta = fabs(topLeftCoord.latitude - bottomRightCoord.latitude) * 1.1; // Add a little extra space on the sides 
    region.span.longitudeDelta = fabs(bottomRightCoord.longitude - topLeftCoord.longitude) * 1.1; // Add a little extra space on the sides 

    region = [mapView regionThatFits:region]; 
    [mapView setRegion:region animated:YES]; 
} 
+0

完美!德爾塔是我能看到的問題。非常感謝! – runmad 2010-10-29 14:47:34

+1

不幸的是,這個頁面似乎沒有迴應。有沒有人有頁面的緩存版本?謝謝! – jowie 2011-08-21 22:17:34

+0

@jowie我能夠使用回機器找到頁面的緩存版本。我希望這有幫助。 http://web.archive.org/web/20100612181520/http://codisllc。com/blog/zoom-mkmapview-to-fit-annotations – avelis 2013-04-04 21:00:52

0

不要被兩個第一線感到害怕,你可以忽略什麼是權=跡象,因爲這將在下面覆蓋...

我認爲這個問題是在這裏:

region.span.longitudeDelta = 0.0; 
+0

是的,上面的Aaron的鏈接有正確計算的增量,它似乎解決了它。只需要調整額外的餘量,但代碼是完美的! – runmad 2010-10-29 14:47:19

1

對於iOS7轉發做到這一點,最好的辦法是:

//from API docs: 
//- (void)showAnnotations:(NSArray *)annotations animated:(BOOL)animated NS_AVAILABLE(10_9, 7_0); 
[self.mapView showAnnotations:self.mapView.annotations animated:YES]; 

對於我的個人項目(之前IO S7)我只是在MKMapView類中添加了一個類別來封裝「可見區域」功能,以進行非常常見的操作:將其設置爲能夠查看MKMapView實例上的所有當前加載的註釋(這包括與您一樣多的引腳可能已放置,以及用戶的位置)。結果是這樣的:

.h文件中

#import <MapKit/MapKit.h> 

@interface MKMapView (Extensions) 

-(void)ij_setVisibleRectToFitAllLoadedAnnotationsAnimated:(BOOL)animated; 
-(void)ij_setVisibleRectToFitAnnotations:(NSArray *)annotations animated:(BOOL)animated; 


@end 

.m文件

#import "MKMapView+Extensions.h" 

@implementation MKMapView (Extensions) 

/** 
* Changes the currently visible portion of the map to a region that best fits all the currently loadded annotations on the map, and it optionally animates the change. 
* 
* @param animated is the change should be perfomed with an animation. 
*/ 
-(void)ij_setVisibleRectToFitAllLoadedAnnotationsAnimated:(BOOL)animated 
{ 
    MKMapView * mapView = self; 

    NSArray * annotations = mapView.annotations; 

    [self ij_setVisibleRectToFitAnnotations:annotations animated:animated]; 

} 


/** 
* Changes the currently visible portion of the map to a region that best fits the provided annotations array, and it optionally animates the change. 
    All elements from the array must conform to the <MKAnnotation> protocol in order to fetch the coordinates to compute the visible region of the map. 
* 
* @param annotations an array of elements conforming to the <MKAnnotation> protocol, holding the locations for which the visible portion of the map will be set. 
* @param animated wether or not the change should be perfomed with an animation. 
*/ 
-(void)ij_setVisibleRectToFitAnnotations:(NSArray *)annotations animated:(BOOL)animated 
{ 
    MKMapView * mapView = self; 

    MKMapRect r = MKMapRectNull; 
    for (id<MKAnnotation> a in annotations) { 
     ZAssert([a conformsToProtocol:@protocol(MKAnnotation)], @"ERROR: All elements of the array MUST conform to the MKAnnotation protocol. Element (%@) did not fulfill this requirement", a); 
     MKMapPoint p = MKMapPointForCoordinate(a.coordinate); 
     //MKMapRectUnion performs the union between 2 rects, returning a bigger rect containing both (or just one if the other is null). here we do it for rects without a size (points) 
     r = MKMapRectUnion(r, MKMapRectMake(p.x, p.y, 0, 0)); 
    } 

    [mapView setVisibleMapRect:r animated:animated]; 

} 

@end 

正如你所看到的,我已經添加2種方法至今:一個用於設置的可見區域映射到適合MKMapView實例上所有當前加載的批註的映射,以及將其設置爲任何對象數組的另一種方法。 所以設置的MapView的可視區域,則代碼將簡單:

//the mapView instance 
    [self.mapView ij_setVisibleRectToFitAllLoadedAnnotationsAnimated:animated]; 

我希望它有助於=)