将注释从显示图像交换到默认引脚

时间:2015-05-12 10:13:45

标签: ios mapkit mkannotationview

当通过模拟器测试地图时,我注意到一些注释显示默认引脚而不是自定义图像。当我回到应用程序主菜单并再次进入mapview时,不同的注释会发生同样的事情。

此代码提供了20个我自己使用相同代码的注释。

-(void)viewDidLoad {

[super viewDidLoad];

_locationManager = [[CLLocationManager alloc] init];
[mapView setDelegate:self];
[mapView setMapType:MKMapTypeStandard];
[mapView setZoomEnabled:YES];
[mapView setScrollEnabled:YES];

MKCoordinateRegion test1 = { {0.0, 0.0} , {0.0, 0.0} };
test1.center.latitude = 55.705609;
test1.center.longitude = 13.195707;
[mapView setRegion:test1 animated:YES];

testmap *ann2 = [[testmap alloc] init];
ann2.title = @"test1";
ann2.subtitle = @"Klicka här för mer info";
ann2.coordinate = test1.center;
ann2.name = @"test1";
[mapView addAnnotation:ann2];

MKCoordinateRegion test2 = { {0.0, 0.0} , {0.0, 0.0} }; //ändra ner
test2.center.latitude = 55.710113;
test2.center.longitude = 13.213500;
[mapView setRegion:test2 animated:YES];

testmap *ann3 = [[testmap alloc] init];
ann3.title = @"test2";
ann3.subtitle = @"Klicka här för mer info";
ann3.coordinate = test2.center;
ann3.name = @"test2";
[mapView addAnnotation:ann3];

MKCoordinateRegion test3 = { {0.0, 0.0} , {0.0, 0.0} };
test3.center.latitude = 55.708981;
test3.center.longitude = 13.197266;
[mapView setRegion:test3 animated:YES];

testmap *ann4 = [[testmap alloc] init];
ann4.title = @"test3";
ann4.subtitle = @"Klicka här för mer info";
ann4.coordinate = test3.center;
ann4.name = @"test3";
[mapView addAnnotation:ann4];

MKCoordinateRegion test4 = { {0.0, 0.0} , {0.0, 0.0} }; //ändra ner
test4.center.latitude = 55.705170;
test4.center.longitude = 13.191277;
[mapView setRegion:test4 animated:YES];

testmap *ann5 = [[testmap alloc] init];
ann5.title = @"test4";
ann5.subtitle = @"Klicka här för mer info";
ann5.coordinate = test4.center;
ann5.name = @"test4";
[mapView addAnnotation:ann5];
}

- (MKAnnotationView *)mapView:(MKMapView *)mapview viewForAnnotation:(id <MKAnnotation>)annotation

{

if ([annotation isKindOfClass:[MKUserLocation class]])
    return nil;
static NSString* AnnotationIdentifier = @"AnnotationIdentifier";
MKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:AnnotationIdentifier];




if(annotationView)
    return nil;
else
{
    MKAnnotationView *annotationView = [[MKAnnotationView alloc] initWithAnnotation:annotation


  reuseIdentifier:AnnotationIdentifier];    annotationView.canShowCallout = YES;
   NSString* thisModelName = ((testmap*)annotation).name;

    if ([thisModelName isEqualToString:@"test1"]) {
    annotationView.image = [UIImage imageNamed:@"test1"];
    UIButton* rightButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];

        [rightButton setTitle:annotation.title forState:UIControlStateNormal];
        annotationView.rightCalloutAccessoryView = rightButton;
        annotationView.canShowCallout = YES;
        annotationView.draggable = YES;
        annotationView.highlighted = YES;

    return annotationView;
    }
    else if ([thisModelName isEqualToString:@"test2"])
    {
        annotationView.image = [UIImage imageNamed:@"test2"];
        UIButton* rightButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];
        [rightButton addTarget:self action:@selector(myButton:) forControlEvents:UIControlEventTouchUpInside];
        [rightButton setTitle:annotation.title forState:UIControlStateNormal];
        annotationView.rightCalloutAccessoryView = rightButton;
        annotationView.canShowCallout = YES;
        annotationView.draggable = YES;
        annotationView.highlighted = YES;
        return annotationView;
    }
    else if ([thisModelName isEqualToString:@"test3"])
    {
        annotationView.image = [UIImage imageNamed:@"test3"];
        UIButton* rightButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];
        [rightButton addTarget:self action:@selector(myButton:) forControlEvents:UIControlEventTouchUpInside];
        [rightButton setTitle:annotation.title forState:UIControlStateNormal];
        annotationView.rightCalloutAccessoryView = rightButton;
        annotationView.canShowCallout = YES;
        annotationView.draggable = YES;
        annotationView.highlighted = YES;
        return annotationView;
    }

     else if ([thisModelName isEqualToString:@"test4"])
    {
        annotationView.image = [UIImage imageNamed:@"test4"];
        UIButton* rightButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];
        [rightButton addTarget:self action:@selector(myButton:) forControlEvents:UIControlEventTouchUpInside];
        [rightButton setTitle:annotation.title forState:UIControlStateNormal];
        annotationView.rightCalloutAccessoryView = rightButton;
        annotationView.canShowCallout = YES;
        annotationView.draggable = YES;
        annotationView.highlighted = YES;
        return annotationView;
    }
    }


     return nil;


     }

1 个答案:

答案 0 :(得分:1)

由于此代码,您将“随机”获取默认引脚:

MKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:AnnotationIdentifier];

if (annotationView)
    return nil;

此代码说的是dequeueReusableAnnotationViewWithIdentifier:返回视图(即如果annotationView nil),则返回nil委托方法。


当您从nil委托方法返回viewForAnnotation时,地图视图会执行以下操作:

  • 如果注释类型为MKUserLocation,则会显示默认的蓝点。
  • 如果注释不是MKUserLocation,则会显示默认的红色针脚。

你可能意味着什么

MKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:AnnotationIdentifier];

if (annotationView)
    return annotationView;

然而 ,这会产生新问题,因为如果dequeue返回一个视图(以前用于不同<的视图) / em>注释),出列视图的image可能与当前annotation应使用的图像不匹配。

因此,当您缩放并平移地图时,注释图像将“随机”切换。

viewForAnnotation中的正确方法是:

  1. 使用dequeueReusableAnnotationViewWithIdentifier:获取对视图的引用,如果返回nil,则创建一个新视图。仅在创建新视图时设置所有注释通用的视图属性。
  2. 使用步骤1中获取的视图参考,设置特定于当前annotation的视图属性。如果正在使用出列视图,请同时更新其annotation属性。
  3. 示例:

    - (MKAnnotationView *)mapView:(MKMapView *)mapview viewForAnnotation:(id <MKAnnotation>)annotation
    {
        if (! [annotation isKindOfClass:[testmap class]])
        {
            //If annotation is NOT a "testmap" (eg. MKUserLocation),
            //return nil so map view displays default view for it...
            return nil;
        }
    
        static NSString* AnnotationIdentifier = @"AnnotationIdentifier";
    
        MKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:AnnotationIdentifier];
    
        if (! annotationView) {
            annotationView = [[MKAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:AnnotationIdentifier];
            //set view properties common to all annotations...
            annotationView.canShowCallout = YES;
            UIButton* rightButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];
            //Do not use addTarget with a custom method for callout accessories.
            //Instead, use the calloutAccessoryControlTapped delegate method shown below.
            annotationView.rightCalloutAccessoryView = rightButton;
            annotationView.draggable = YES;
        }
        else {
            //reusing a view, update its annotation to current...
            annotationView.annotation = annotation;
        }
    
        //AFTER we have a view reference, set annotation-specific properties...
        NSString* thisModelName = ((testmap*)annotation).name;
    
        if ([thisModelName isEqualToString:@"test1"]) {
            annotationView.image = [UIImage imageNamed:@"test1"];
        }
        else if ([thisModelName isEqualToString:@"test2"]) {
            annotationView.image = [UIImage imageNamed:@"test2"];
        }
        else if ([thisModelName isEqualToString:@"test3"]) {
            annotationView.image = [UIImage imageNamed:@"test3"];
        }
        else if ([thisModelName isEqualToString:@"test4"]) {
            annotationView.image = [UIImage imageNamed:@"test4"];
        }
        /*
         If image name will always be same as `name` property then
         can use single line instead of if/else statements:
    
             annotationView.image = [UIImage imageNamed:thisModelName];
         */
    
        return annotationView;
    }
    
    -(void)mapView:(MKMapView *)mapView annotationView:(MKAnnotationView *)view calloutAccessoryControlTapped:(UIControl *)control
    {
        if ([view.annotation isKindOfClass:[testmap class]]) {
            testmap *tm = (testmap *)view.annotation;
            NSLog(@"button for '%@' tapped", tm.name);
        }
    }