2012-07-02 2 views
2

Я новый парень в области XCode и задавался вопросом, может ли кто-нибудь помочь мне.removeOverlay: overlay not working

По существу, я играю с примером проекта TileMap в WWDC2010 и пытаюсь выяснить способ скрыть их диаграмму NOAA с помощью сегментированного контроллера.

Я могу активировать оверлей, и он отображается нормально, но я не могу в течение жизни удалить его с помощью сегментированного контроллера.

Вот некоторый код из заголовочного файла:

@interface ViewController : UIViewController <MKMapViewDelegate> { 
    IBOutlet MKMapView *map; 
    IBOutlet UISegmentedControl *controller; 
}  
- (IBAction)switchMap:(id)sender; 
@end 

и здесь нет код для .m:

- (void)viewDidLoad { 
    [super viewDidLoad]; 
    NSLog(@"initial view loaded"); 
} 

- (MKOverlayView *)mapView:(MKMapView *)mapView viewForOverlay:(id)overlay { 

    TileOverlayView *view = [[TileOverlayView alloc] initWithOverlay:overlay];  
    view.tileAlpha = 1; 
    return view; 
} 

- (void)viewDidUnload 
{ 
    [super viewDidUnload]; 
    // Release any retained subviews of the main view. 
} 

- (BOOL)shouldAutorotateToInterfaceOrientation:  (UIInterfaceOrientation)interfaceOrientation 
{ 
    return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown); 
} 

- (IBAction)switchMap:(id)overlay { 

    if (controller.selectedSegmentIndex == 0) { 
     NSLog(@"welp... it loaded..."); 
     [map removeOverlay:overlay]; 
    } 

    if (controller.selectedSegmentIndex == 1) { 

     NSLog(@"Map Overlay works"); 
     NSString *tileDirectory = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"Tiles"]; 
     TileOverlay *overlay = [[TileOverlay alloc] initWithTileDirectory:tileDirectory]; 
     [map addOverlay:overlay]; 

     MKMapRect visibleRect = [map mapRectThatFits:overlay.boundingMapRect]; 
     visibleRect.size.width /= 2; 
     visibleRect.size.height /= 2; 
     visibleRect.origin.x += visibleRect.size.width/2; 
     visibleRect.origin.y += visibleRect.size.height/2; 
     map.visibleMapRect = visibleRect; 

    } 


    if (controller.selectedSegmentIndex == 2) { 
     NSLog(@"But... overlay isnt hiding waa"); 
     NSString *tileDirectory = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"Tiles"]; 
     TileOverlay *overlay = [[TileOverlay alloc] initWithTileDirectory:tileDirectory]; 
     [map removeOverlay:overlay]; } 
    } 

ответ

1

В способе управления действия, первый параметр (независимо от того, что вы имя он) всегда является объектом, который называется методом.

Здесь элемент управления является UISegmentedControl, поэтому параметр, который передается в switchMap:, является ссылкой на этот элемент управления. В .h вы объявили параметр с именем sender, но в .m его назвали overlay.

Независимо от имени, это все еще сегментированный объект управления, поэтому передача его в removeOverlay бессмысленна и ничего не будет делать.


Так что в этом коде:

if (controller.selectedSegmentIndex == 0) { 
    NSLog(@"welp... it loaded..."); 
    [map removeOverlay:overlay]; 
} 

overlay указывает на сегментированной управления и поэтому removeOverlay ничего не делает.


В этом коде:

if (controller.selectedSegmentIndex == 2) { 
    NSLog(@"But... overlay isnt hiding waa"); 
    NSString *tileDirectory = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"Tiles"]; 
    TileOverlay *overlay = [[TileOverlay alloc] initWithTileDirectory:tileDirectory]; 
    [map removeOverlay:overlay]; } 

Вы создаете новый локальный overlay объект (компилятор, вероятно, также дает вам предупреждение о локальной переменной, скрывающей параметр). Этот новый объект отделен от наложения, которое уже было добавлено на карту. Вызов removeOverlay на этом новом объекте ничего не делает, потому что этот новый экземпляр никогда не был добавлен на карту в первую очередь.


Чтобы удалить существующую накладку, вы должны либо сохранить ссылку Ивара к нему, когда вы добавляете его и передать, что Ивар, чтобы удалить или найти его в overlays массиве вида карты в.

Однако, если вы когда-либо будет только один оверлей, вы можете пройти первый объект в overlays массиве вид карты или просто позвоните removeOverlays (во множественном числе) и передать весь массив:

if (map.overlays.count > 0) 
    [map removeOverlay:[map.overlays objectAtIndex:0]]; 

//OR... 

if (map.overlays.count > 0) 
    [map removeOverlays:map.overlays]; 
+0

спасибо Анне, что многое прояснилось для меня. Я все еще новичок во всем этом, и этот ответ не только ответил на мой вопрос, но и я многому научился у него. Благодаря! –