MKAnnotationView及其rightCalloutAccessoryView之间的布局关系在iOS7中已更改

时间:2013-09-29 17:49:53

标签: ios ios7 mkannotationview

UIButton设置为rightCalloutAccessoryView的{​​{1}},并触发MKPinAnnotationView方法。在iOS6中,btnClicked:及其MKAnnotationView之间的布局关系可以轻松用于查找rightCalloutAccessoryViewMKPinAnnotationView。但是在iOS7中,布局关系不再存在。

MKPinAnnotationView *pin = (MKPinAnnotationView *)[[button superview] superview];

登录iOS6:

- (MKAnnotationView *)mapView:(MKMapView *)theMapView viewForAnnotation:(id <MKAnnotation>)annotation{
...

MKPinAnnotationView *pinView = (MKPinAnnotationView *)[mapView dequeueReusableAnnotationViewWithIdentifier:tripStartAddrAnnotationIdentifier];
    if (!pinView)
    {            
        MKPinAnnotationView *customPinView = [[MKPinAnnotationView alloc]
                                              initWithAnnotation:annotation reuseIdentifier:tripStartAddrAnnotationIdentifier];
        customPinView.animatesDrop = NO;
        customPinView.canShowCallout = YES;

        UIButton* rightButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, 32, 32)];
        [rightButton setImage:[UIImage imageNamed:@"disclosureUpMap.png"] forState:UIControlStateNormal];
        [rightButton setImage:[UIImage imageNamed:@"disclosureDownMap.png"] forState:UIControlStateNormal];

        [rightButton addTarget:self
                        action:@selector(btnClicked:)
              forControlEvents:UIControlEventTouchUpInside];
        customPinView.rightCalloutAccessoryView = rightButton;

        return customPinView;
    }
    else
    {
        pinView.annotation = annotation;
    }
    return pinView;
...
}


-(void)btnClicked:(id)sender{
    NSLog(@"superview 1 :%@",[sender superview]);
    NSLog(@"superview 2 :%@",[[sender superview] superview]);
    NSLog(@"superview 3 :%@",[[[sender superview] superview] superview]);
    NSLog(@"superview 4 :%@",[[[[sender superview] superview] superview] superview]);
    MKPinAnnotationView *pin = (MKPinAnnotationView *)[[sender superview] superview];
    // the information contains in pin.annotation is necessary for the pushed view controller
...    
}

登录iOS7:

2013-09-30 01:21:11.851 MyApp[6113:c07] superview 1 :<UICalloutView: 0x1e3df250; frame = (-246 -60; 320 70); clipsToBounds = YES; layer = <CALayer: 0x1e3e0140>>
2013-09-30 01:21:11.851 MyApp[6113:c07] superview 2 :<MKPinAnnotationView: 0x1b649510; frame = (526 223; 32 39); layer = <MKLayer: 0x1b649570>> visible:1 +33.19910200, +120.45132100
2013-09-30 01:21:11.852 MyApp[6113:c07] superview 3 :<MKAnnotationContainerView: 0xb68b380; frame = (0 0; 640 640); autoresizesSubviews = NO; layer = <CALayer: 0xb68b410>>
2013-09-30 01:21:11.852 MyApp[6113:c07] superview 4 :<MKScrollContainerView: 0xb68c8f0; frame = (-280 -72.5; 640 640); autoresizesSubviews = NO; layer = <CALayer: 0xb68c980>>

任何帮助将不胜感激。

1 个答案:

答案 0 :(得分:4)

这是使用地图视图自己的委托方法calloutAccessoryControlTapped而非自定义方法的一个很好的理由。

即使superview方法适用于iOS 6或更早版本,依赖特定的视图层次结构通常也是一个坏主意。

委托方法可以方便地提供对注释视图的引用,您可以通过view.annotation从中获取注释(无需猜测或希望或假设)。

删除addTarget并使用委托方法替换自定义方法。

如果你必须使用自定义方法而不是委托方法,那么从地图视图的selectedAnnotations属性中获取所选注释会更加可靠,而不是查找超级视图。