2012-05-27 14 views
13

Quindi ho un MKMapView con tutti i miei pin aggiunti e il colore del pin dipende dal fatto che sia impostato un valore per quel pin. Quando carico l'app, viene chiamato viewForAnnotation e i colori vengono impostati di conseguenza. Tuttavia, quando aggiorno i dettagli del pin (come posizione, titolo, ecc ...) aggiorno anche il pinColour per trovarlo non aggiornato. Sembra che viewForAnnotation non venga richiamato dopo l'aggiunta iniziale.Forza MKMapView viewForAnnotation per aggiornare

Ho letto molte domande simili a questo e posso confermare che mapView.delegate = self;

Ecco il mio codice viewForAnnotation:

- (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(MapAnnotation *)annotation 
{ 
    if([annotation class] == MKUserLocation.class) 
     return nil; 

    NSString *pinIdentifier = annotation.identifier; // This is a unique string for each pin and is getting populated every time! 

    MKPinAnnotationView *annotationView = (MKPinAnnotationView *) [mapView dequeueReusableAnnotationViewWithIdentifier:pinIdentifier]; 

    if(annotationView == nil) 
     annotationView = [[MKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:pinIdentifier]; 
    else 
     annotationView.annotation = annotation; // Never had this line fire... 

    annotationView.canShowCallout = YES; 
    annotationView.animatesDrop = NO; 
    annotationView.enabled = YES; 
    annotationView.tag = annotation.counter; 

    if(annotation.pinColour == Stopped) // from enum 
     annotationView.pinColor = MKPinAnnotationColorRed; 
    else 
     annotationView.pinColor = MKPinAnnotationColorGreen; 

    UIButton *infoButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure]; 
    [infoButton addTarget:self action:@selector(mapCalloutButtonPressed:) forControlEvents:UIControlEventTouchUpInside]; 
    infoButton.tag = annotation.counter; 
    annotationView.rightCalloutAccessoryView = infoButton; 

    return annotationView; 
} 

Ecco il codice in cui aggiungo il perno:

CLLocationCoordinate2D annotationCoord; 
annotationCoord.latitude = latestPosition.latitude; 
annotationCoord.longitude = latestPosition.longitude; 

MapAnnotation *annotation = [[MapAnnotation alloc] init]; 
annotation.coordinate = annotationCoord; 
annotation.identifier = theIdentifier; 
annotation.title = theTitle; 
annotation.subtitle = theSubtitle 
annotation.pinColour = [self getPinColour]; 
annotation.counter = theCounter; 

[theMapView addAnnotation:annotation]; 

Ecco il codice in cui aggiorno il pin (metodo diverso da aggiungere):

updatePin = true; 
pinCounter = mapPin.counter; 

CLLocationCoordinate2D annotationCoord; 
annotationCoord.latitude = latestPosition.latitude; 
annotationCoord.longitude = latestPosition.longitude; 
[mapPin setCoordinate:annotationCoord]; 

mapPin.identifier = theIdentifier; 
mapPin.subtitle = theSubtitle; 
mapPin.pinColour = [self getPinColour]; 

Non sono sicuro di cosa mi manchi. viewForAnnotation è ovviamente funzionante, non è mai stato chiamato dopo l'aggiunta iniziale! Se dovesse chiamare questa funzione sono sicuro al 100% che funzionerebbe come cambia colore se riavviavo l'app!

EDIT: Oh e davvero non voglio iniziare a rimuovere le annotazioni e riaggiungerle. È quello che sto facendo a breve termine comunque!

risposta

12

A causa del modo in cui la vista mappa memorizza nella cache le sue annotazioni, è necessario rimuovere e aggiungere nuovamente l'annotazione se è necessario apportare modifiche al suo aspetto. Un semplice rimuovere & aggiungere è la strada da percorrere. Non esiste un meccanismo di invalidamento della cache, ma questo.

+0

Ah, grazie. Non volevo davvero farlo in quel modo, ma sono riuscito a mantenere la vista del callout, quindi ora non puoi dirlo comunque! Segnalo come risposta, perché non sapevo che quello era l'unico modo. –

+0

No, non è la risposta corretta, vedi sotto –

+0

Questo non funziona. – Aggressor

36

In realtà, non so se questo ha funzionato per te, ma è così che l'ho fatto.

Non ho bisogno di eliminare l'annotazione dalla mappa. Tutto quello che devo fare è dire alla mappa di darmi la vista di annotazione per un'annotazione di parametro. La mappa restituirà l'annotazione corretta. Da lì, ho una proprietà per la mia annotazione personalizzata per identificare se si tratta di un elemento attivo, se sì, mostra la normale immagine pin, altrimenti mostra l'immagine pin completa.

-(void)updateAnnotationImage:(CustomAnnotation *)paramAnnotation 
{ 
    MKAnnotationView *av = [geoMap viewForAnnotation:paramAnnotation]; 

    if (paramAnnotation.active) 
    { 
     av.image = [UIImage imageNamed:@"PinNormal.png"]; 
    } 
    else 
    { 
     av.image = [UIImage imageNamed:@"PinFull.png"]; 
    } 
} 

Un po 'in ritardo, ma si spera che aiuti gli altri che hanno riscontrato questo problema.

+0

Questo è possibile e questo è il modo corretto .. +1 per la risposta. –

+0

Questa dovrebbe essere la risposta accettata. Grazie! – lostintranslation

0

Swift 2.1:

Ho avuto lo stesso problema, e hanno trovato una soluzione rapida, attivare questo momento necessario, anche inviarlo al thread principale sarebbe saggio:

var annotationsArray = mapView.annotations 
mapView.removeAnnotations(mapView.annotations) 
mapView.addAnnotations(arrayIncs) 
arrayIncs.removeAll() 
Problemi correlati