2012-08-02 44 views
1

我到目前爲止所做的工作正在工作,但我想知道這是否正確的方式。如何正確地從另一個viewController刪除一個引腳

我有一張地圖,顯示一個註釋,當它被按下時顯示一個標註。

顯示的下一個視圖是一個表視圖。該表格有一個按鈕可以刪除該註釋。

我在表格視圖中創建了一個屬性MKMapView。在點擊callOut附件後初始化此視圖後,我設置MKMapView屬性。

當在表格視圖中按下按鈕時,我通過地圖屬性刪除註釋。

這是正確的方法嗎?

回答

1

而不是直接操作父(map)控制器視圖的控件的詳細視圖,更「正確」的方法可能是使用委託+協議。

用地圖控制器需要實現的方法定義協議(例如,deleteAnnotation,detailViewDone等)。

詳細視圖將具有該協議的委託屬性,並通過委託屬性調用協議方法,而不是直接訪問和修改其他視圖的控件。

地圖控制器將自己設置爲詳細視圖的委託並實際實現協議方法。這樣,每個控制器/類不必知道其他人如何工作的內部細節,讓你更容易地改變每個人的內部工作方式,而不會影響其他人的代碼(只要協議不會影響其他人的工作,改變)。它提高了封裝和可重用性。

例如,在詳細視圖中.H,定義協議和聲明代表屬性:

@protocol DetailViewControllerDelegate <NSObject> 
-(void)deleteAnnotation:(id<MKAnnotation>)annotation; 
-(void)detailViewDone; 
//could have more methods or change/add parameters as needed 
@end 

@interface DetailViewController : UIViewController 
@property (nonatomic, assign) id<DetailViewControllerDelegate> delegate; 
@end 

在詳細視圖中的.m,不管你處理刪除按鈕時,調用該委託方法來代替:

if ([delegate respondsToSelector:@selector(deleteAnnotation:)]) 
{ 
    [delegate deleteAnnotation:annotation]; 
} 

在地圖控制器.H,聲明它實現的協議和聲明的方法:

@interface MapViewController : UIViewController<DetailViewControllerDelegate> 
-(void)deleteAnnotation:(id<MKAnnotation>)annotation; 
-(void)detailViewDone;  
@end 
在地圖控制器的.m

DetailViewController *dvc = [[DetailViewController alloc] init... 
dvc.annotation = view.annotation; 
dvc.delegate = self; 
[self presentModalViewController:dvc animated:YES]; 

最後,還實現委託方法:

在地圖控制器.M,在您創建的詳細視圖calloutAccessoryControlTapped,設置委託屬性,而不是地圖視圖屬性:

-(void)deleteAnnotation:(id<MKAnnotation>)annotation 
{ 
    [mapView removeAnnotation:annotation]; 
    //dismiss the detail view (if that's what you want)... 
    [self dismissModalViewControllerAnimated:YES]; 
} 

從文檔,文章Delegates and Data SourcesUsing Delegation to Communicate with Other Controllers可能是有用的。

+0

感謝您的優秀解釋。迄今爲止,這比我學到的要先進得多。但是,它很瞭解它。謝謝 – Camus 2012-08-03 15:42:11

+0

還有一個問題Anna,爲什麼你設置dvc.annotation如果你沒有聲明它是一個屬性。謝謝 – Camus 2012-08-05 08:40:22

+0

我假設你已經在細節控制器上擁有這樣一個屬性,所以它知道要顯示哪個註釋。如果沒有,你可以添加它。 – Anna 2012-08-05 14:43:07

相關問題