点击Listeners in Loop for rectangle array -- Closure

Click Listeners in Loop for rectangle array -- Closure

我的问题与此非常相似 post 但由于某种原因该解决方案对我不起作用 --> Click Listeners in Loop - Array and Closure

用户可以点击google地图api;我想在用户点击的任何地方制作 2kmx2km 的矩形,将它们添加到矩形数组中,并为它们添加监听器以进行点击。矩形出现并且矩形数组被填充,但只有点击监听器。不。工作。我束手无策,不断研究和尝试各种解决方案;任何帮助将不胜感激!

var SFLatLng = {lat: 37.7739, lng: -122.4312};
var map;
var rectangleArray = [];
var rectangleArraySize = 0;

function initMap() {
    map = new google.maps.Map(document.getElementById('map'), {
         center: SFLatLng,
         zoom: 12,
         scaleControl: true,
    });
    doStuff();
} //end map init

function doStuff() {
      //make rectangle of size 2kmx2km on map click
      map.addListener('click', function(e) {      
   var bounds = calcBounds(e.latLng, new google.maps.Size(2000,2000));
   addRectangleToMap(bounds);
      });

     function addRectangleToMap(boundsObj) {
  rectangleArray[rectangleArraySize] = {
       rect: new google.maps.Rectangle({
   map: map,
                 bounds: boundsObj,
                 fillColor:'red',
                 fillOpacity: 0.3,
                 strokeOpacity: 0,
                 clickable: true,
                 zIndex: 1
    })
   };
   rectangleArraySize++;
     }

     function addClickListener(rectObj) {
         google.maps.event.addListener(rectObj.rect, 'click', function() {
              alert("clicked!")
         });
     }

     for (var i = 0; i < rectangleArray.length; i++ ) {       
          if(rectangleArray[i]) { //safety
              addClickListener(rectangleArray[i]);
          }       
     }
}

/** @this {google.maps.Rectangle} */
function calcBounds(center,size){
    //Calculates bounds ...
}

这样使用immediately-invoked-function-expression(IIFE),可以立即绑定rectObj的值。

function addClickListener(rectObj) {

    (function(rectObj) {
        google.maps.event.addListener(rectObj.rect, 'click', function() {
            alert("clicked!")
        });
    })(rectObj)
}

您需要在矩形上调用 addClickListener 函数。

function addRectangleToMap(boundsObj) {
  rectangleArray[rectangleArraySize] = {
      rect: new google.maps.Rectangle({
      map: map,
      bounds: boundsObj,
      fillColor:'red',
      fillOpacity: 0.3,
      strokeOpacity: 0,
      clickable: true,
      zIndex: 1
    })
  };
  addClickListener(rectangleArray[rectangleArraySize]);
  rectangleArraySize++;
}

proof of concept fiddle

代码片段:

var SFLatLng = {
  lat: 37.7739,
  lng: -122.4312
};
var map;
var rectangleArray = [];
var rectangleArraySize = 0;
var infowindow = new google.maps.InfoWindow();

function initMap() {
    map = new google.maps.Map(document.getElementById('map'), {
      center: SFLatLng,
      zoom: 12,
      scaleControl: true,
    });
    doStuff();
  } //end map init

function doStuff() {
  //make rectangle of size 2kmx2km on map click
  map.addListener('click', function(e) {
    var bounds = calcBounds(e.latLng, new google.maps.Size(2000, 2000));
    addRectangleToMap(bounds);
  });

  function addRectangleToMap(boundsObj) {
    rectangleArray[rectangleArraySize] = {
      rect: new google.maps.Rectangle({
        map: map,
        bounds: boundsObj,
        fillColor: 'red',
        fillOpacity: 0.3,
        strokeOpacity: 0,
        clickable: true,
        zIndex: 1
      })
    };
    addClickListener(rectangleArray[rectangleArraySize]);
    rectangleArraySize++;
  }

  function addClickListener(rectObj) {
    google.maps.event.addListener(rectObj.rect, 'click', function() {
      // alert("clicked!");
      infowindow.setContent("clicked:<br>" + this.getBounds().toUrlValue());
      infowindow.setPosition(this.getBounds().getCenter());
      infowindow.open(map);

    });
  }

  for (var i = 0; i < rectangleArray.length; i++) {
    if (rectangleArray[i]) { //safety
      addClickListener(rectangleArray[i]);
    }
  }
}

/** @this {google.maps.Rectangle} */

function calcBounds(center, size) {
  var obj = {
    south: 37.70339999999999,
    west: -122.52699999999999,
    north: 37.812,
    east: -122.3482,
    lat: 37.7749295,
    lng: -122.4194155
  };
  if (rectangleArray.length == 0) {
    var bounds = new google.maps.LatLngBounds(new google.maps.LatLng(obj.south, obj.west), new google.maps.LatLng(obj.lat, obj.lng));
  } else {
    var bounds = new google.maps.LatLngBounds(new google.maps.LatLng(obj.lat, obj.lng), new google.maps.LatLng(obj.north, obj.east));
  }
  console.log(bounds.toUrlValue());
  //Calculates bounds ...
  return bounds;
}
google.maps.event.addDomListener(window, "load", initMap);
html,
body,
#map {
  height: 100%;
  width: 100%;
  margin: 0px;
  padding: 0px
}
<script src="https://maps.googleapis.com/maps/api/js"></script>
<div id="map"></div>