19

I am working on a webapplication. I have a google map, where I add polygons from an array. I loop through that array and add the polygons to the map. I also need to add an event listener to the polygon click and alert the position of the polygon

This is what I'm doing

map = new google.maps.Map(document.getElementById('map_canvas'),
    mapOptions);
//Loop on the polygonArray
for (var i = 0; i < polygonArray.length; i++) {
    //Add the polygon
    var p = new google.maps.Polygon({
        paths: polygonArray[i],
        strokeWeight: 0,
        fillColor: '#FF0000',
        fillOpacity: 0.6,
        indexID: i
    });
    p.setMap(map);

    //Add the click listener
    google.maps.event.addListener(p, 'click', function (event) {
        //alert the index of the polygon
        alert(p.indexID);
    });
}

Problem

The polygons are all drawing correctly. However the problem is that when I try to click on a polygon it always shows the last index. it is like it is only clicking on the last polygon added. I think when I add a new listener it overrides the old one. How can I add a listener for each polygon added in order to alert the correct index?

Thanks

Y2theZ
  • 10,162
  • 38
  • 131
  • 200
  • possible duplicate of [Open InfoWindow for each polygon google maps V3](http://stackoverflow.com/questions/13017915/open-infowindow-for-each-polygon-google-maps-v3) – geocodezip Mar 04 '13 at 19:24
  • The essence of this issue is that the same `p` is shared by all `function(event)` closures _as well as the loop block_ . Thus, `p` is bound to the last created polygon when the loop executes. I'd use `polygonArray.forEach` to separate the variables. – Ross Rogers Mar 07 '16 at 17:18
  • 1
    use `let` rather than `var` – Amir Sasson May 14 '19 at 16:59

2 Answers2

46

It's the normal behavior. There is two solutions that I can think of :

1) I am sure you can find back the polygon from the context (I didn't test it):

google.maps.event.addListener(polygon, 'click', function (event) {
  alert(this.indexID);
});  

2) You could also use some closures:

var addListenersOnPolygon = function(polygon) {
  google.maps.event.addListener(polygon, 'click', function (event) {
    alert(polygon.indexID);
  });  
}

map = new google.maps.Map(document.getElementById('map_canvas'),
    mapOptions);
//Loop on the polygonArray
for (var i = 0; i < polygonArray.length; i++) {
    //Add the polygon
    var p = new google.maps.Polygon({
        paths: polygonArray[i],
        strokeWeight: 0,
        fillColor: '#FF0000',
        fillOpacity: 0.6,
        indexID: i
    });
    p.setMap(map);
    addListenersOnPolygon(p);
}
Community
  • 1
  • 1
SuperSkunk
  • 1,268
  • 12
  • 24
1

Move the code block inside the for-loop.

//Add the click listener
    google.maps.event.addListener(p, 'click', function (event) {
        //alert the index of the polygon
        alert(p.indexID);
    });

OR

You add this to for-loop,

p.addListener('click', clickSelection);

and do this

function clickSelection(){
alert("Clicked");
}
Abhi
  • 111
  • 1
  • 6