2009-05-06 6 views
5

Je rencontre des problèmes avec Google Maps/Javascript. Je pense que je sais quel est le problème, mais je ne sais pas comment le contourner.Google Maps Trouble: Fermetures et passages par référence

Un exemple de mon problème est here. Quel que soit le marqueur sur lequel vous cliquez, le second apparaît. Je suis évidemment en train de transmettre la mauvaise info dans mon écouteur d'événement mais je n'arrive pas à trouver le bon code. Voici une partie découpée vers le bas du code:

D'abord, voici une partie de mon code:

if (GBrowserIsCompatible() && mapResults != null) { 
    // Read in the JSON 
    var mapDetailsArray = loadJSON(); 

    // Create a map 
    var map = new google.maps.Map2(document.getElementById(elementId)); 
    map.setCenter(new google.maps.LatLng(mapDetailsArray[0].getLatitude(), 
     mapDetailsArray[0].getLongitude()), 13); 
    map.addControl(new google.maps.SmallMapControl()); 

    // Add the points and center 
    var mgr = new google.maps.MarkerManager(map); 
    var bounds = new google.maps.LatLngBounds(); 
    for (var i = 0; i < mapDetailsArray.length; i++) { 
    var mapDetails = mapDetailsArray[i]; 

    var point = new google.maps.LatLng(mapDetails.getLatitude(), mapDetails 
     .getLongitude()); 
    bounds.extend(point); 

    // Create our marker 
    var marker = new google.maps.Marker(point); 

    // What action do we use to show the hover 
    var infoAction = "mouseover"; 

    marker.value = mapDetails; 

    google.maps.Event.addListener(marker, infoAction, function() { 
     alert(marker.value); 
     map.openInfoWindowHtml(point, getResultInfoContent(marker.value)); 
    }); 

    mgr.addMarker(marker, 1); 
    } 
    mgr.refresh(); 
} 

« marker.value » se termine toujours comme jeu la dernière valeur de ce qui était mapDetails. Si quoi que ce soit, je m'attendrais à ce que ce soit "indéfini" car une fois la boucle terminée, cette valeur ne devrait-elle pas disparaître? J'ai essayé différentes valeurs différentes (par exemple marker.value = i + 1;) mais il apparaîtra toujours comme la même valeur pour les deux points.

Quelqu'un at-il une idée de comment je peux transmettre les valeurs correctes dans l'écouteur d'événements?

Répondre

6

Modifier ceci:

google.maps.Event.addListener(marker, infoAction, function() { 
     alert(marker.value); 
     map.openInfoWindowHtml(point, getResultInfoContent(marker.value)); 
    }); 

à ceci:

google.maps.Event.addListener(marker, infoAction, (function(marker, point, map) { return function() { 
     alert(marker.value); 
     map.openInfoWindowHtml(point, getResultInfoContent(marker.value)); 
    }})(marker, point, map)); 

Cela va créer la fermeture que vous voulez.

Fractionner pour plus de clarté:

var f = function(marker, point, map) 
{ 
    return function() 
    { 
     alert(marker.value); 
     map.openInfoWindowHtml(point, getResultInfoContent(marker.value)); 
    } 
} 

google.maps.Event.addListener(marker, infoAction, f(marker, point, map)); 
+0

qui a fait l'affaire. À la vôtre Greg. J'avais essayé quelque chose comme ça plus tôt mais moins la fonction de retour() {...} enveloppant le code. –

+0

J'ai rencontré le même problème et utilisé le même correctif. Je pense vraiment que c'est un bug en Javascript. – SingleNegationElimination

+0

Je ne pense pas que ce soit un bug, ce n'est pas très intuitif – Greg

3

La réponse ci-dessus n'est pas très intuitive mais - comme l'a dit Greg. Lorsque vous ajoutez un événement à un objet, cet objet est transmis afin que vous puissiez y accéder par "ceci" dans la fermeture. Si vous avez remplacé "marker.value" par "this.value", votre problème aurait été résolu. Si vous avez besoin de transmettre plus de choses, vous attacher à l'objet et le transmettre:

marker.a = 1 
marker.b = 2 
marker.c = 3 

Dans la fermeture this.a sera 1 et ainsi de suite ..