There are a few tutorials and questions on this, but I’m not knowledgeable enough yet to understand how to implement them into my particular app. I get JSON annotation data from a URL and parse it and add each annotation in for loop. I want to add a link on each annotation to open Maps for directions.
Here’s my ViewController.H
#import <UIKit/UIKit.h>
#import <MediaPlayer/MediaPlayer.h>
#import <MapKit/MapKit.h>
//MAP Setup
@interface ViewController : UIViewController <MKMapViewDelegate>
//map setup
@property (weak, nonatomic) IBOutlet MKMapView *mapView;
@property (nonatomic, strong) NSMutableData *downloadData;
//- (IBAction)refreshTapped:(id)sender;
@end
and my ViewController.m
- (void)viewDidLoad
{
////////////////////////
//Connection to download JSON map info
////////////////////////
self.downloadData = [NSMutableData new];
NSURL *requestURL2 = [NSURL URLWithString:@"http:OMITTED"];
NSURLRequest *request = [NSURLRequest requestWithURL:requestURL2];
NSURLConnection *connection = [NSURLConnection connectionWithRequest:request delegate:self];
//scroller
[scroller setScrollEnabled:YES];
[scroller setContentSize:CGSizeMake(320,900)];
[super viewDidLoad];
//Map
[self.mapView.userLocation addObserver:self
forKeyPath:@"location"
options:(NSKeyValueObservingOptionNew|NSKeyValueObservingOptionOld)
context:nil];
}
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
[self.downloadData appendData:data];
}
- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
id parsed = [NSJSONSerialization JSONObjectWithData:_downloadData options:kNilOptions error:nil];
////////////////////////
//Iterating and adding annotations
////////////////////////
for (NSDictionary *pointInfo in parsed)
{
NSLog([pointInfo objectForKey:@"name"]);
double xCoord = [(NSNumber*)[pointInfo objectForKey:@"lat"] doubleValue];
double yCoord = [(NSNumber*)[pointInfo objectForKey:@"lon"] doubleValue];
CLLocationCoordinate2D coords = CLLocationCoordinate2DMake(xCoord, yCoord);
MKPointAnnotation *point = [MKPointAnnotation new];
point.coordinate = coords;
point.title = [pointInfo objectForKey:@"name"];
[self.mapView addAnnotation:point];// or whatever your map view's variable name is
}
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
//centers map on user loc and then allows for movement of map without re-centering on userlocation check.
-(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context{
if ([self.mapView showsUserLocation])
{
MKCoordinateRegion region;
region.center = self.mapView.userLocation.coordinate;
MKCoordinateSpan span;
span.latitudeDelta = .50; // Change these values to change the zoom
span.longitudeDelta = .50;
region.span = span;
[self.mapView setRegion:region animated:YES];
self.mapView.showsUserLocation = NO;}
}
- (void)dealloc
{
[self.mapView.userLocation removeObserver:self forKeyPath:@"location"];
[self.mapView removeFromSuperview]; // release crashes app
self.mapView = nil;
}
@end
Launching the Maps App of the Location Awareness Programming Guide says:
So, you should:
Make sure to define your view controller to be the
delegatefor your map view;Write a
viewForAnnotationthat turns oncanShowCalloutand turns on the callout accessory view:Then write a
calloutAccessoryControlTappedmethod that opens the maps as outlined above, based upon what versions of iOS you’re supporting, e.g., for iOS 6:I don’t know what additional geographic information your have in your KML, but you can presumably fill in the
addressDictionaryas you see fit.In answer to your follow-up question about how to use the
addressDictionaryparameter of theMKPlacemarkinitializer method,initWithCoordinate, if you hadNSStringvariables for the streetaddress, thecity, thestate, thezip, etc., it would look like:For this to work, you have to add the appropriate framework,
AddressBook.framework, to your project and import the header in your .m file:The real question, though, was how to set the
namefor theMKMapItemso it doesn’t show up as “Unknown Location” in the maps app. That’s as simple as setting thenameproperty, probably just grabbing thetitlefrom yourannotation: