0

I am trying to plot markers on a google map using an array of addresses. The markers are correctly plotting (I used the tips in this post: Multiple markers Google Map API v3 from array of addresses and avoid OVER_QUERY_LIMIT while geocoding on pageLoad) but I am getting this error when I try to add information from the addresses array into the marker and infowindow: "TypeError: undefined is not an object (evaluating 'addresses[x][0]')"

The problem appears to be that within the 'for' loop, x evaluates to the length of the array, 4, every time I loop.

The markers and infowindows are working; they show up when I use a string or I use addresses[0], addresses[1], etc., but everything breaks when I try to do addresses[x] because addresses[4] does not exist. Any pointers at how I can iterate through my addresses array to properly set my marker titles and infowindows?

Note: in case it's relevant, there is a reason the addresses variable is declared inside the calcRoute() function.

This is the code:

var directionsDisplay;
var directionsService = new google.maps.DirectionsService();
var map;

function initialize() {
  directionsDisplay = new google.maps.DirectionsRenderer();
  var chicago = new google.maps.LatLng(41.850033, -87.6500523);
  geocoder = new google.maps.Geocoder(); 
  var mapOptions = {
    zoom:7,
    center: chicago
  };
  map = new google.maps.Map(document.getElementById('map-canvas'), mapOptions);
  directionsDisplay.setMap(map);
}

function calcRoute() {
  var start = document.getElementById('start').value;
  var end = document.getElementById('end').value;
  var request = {
    origin:start,
    destination:end,
    travelMode: google.maps.TravelMode.DRIVING
  };
  directionsService.route(request, function(response, status) {
    if (status == google.maps.DirectionsStatus.OK) {
      directionsDisplay.setDirections(response);
      var addresses = [["Beaver Creek Smokehouse","4.5",["601 Main St","Martinez, CA 94553"]],["Lemongrass Bistro","4.5",["501 Main St","Martinez, CA 94553"]],["Picnicky's Sandwich Shop","4.0",["3833 Sonoma Blvd","Vallejo, CA 94590"]],["LV Vietnamese Pho and Sandwiches","4.0",["2621 Springs Rd","Vallejo, CA 94591"]]];
      var infowindow = new google.maps.InfoWindow();
      var marker, x;    

      //This is the problem area:
      for (x = 0; x < addresses.length; x++) {
        jQuery.getJSON('http://maps.googleapis.com/maps/api/geocode/json?address='+addresses[x][2]+'&sensor=false', null, function (data) {
          console.log(x); // logs the length of array, 4, every time
          var p = data.results[0].geometry.location;
          var latlng = new google.maps.LatLng(p.lat, p.lng);

          marker = new google.maps.Marker({
            position: latlng,
            map: map,
            title: 'this works' // markers don't show when I use addresses[x][0]
          });
          google.maps.event.addListener(marker, 'click', (function(marker, x) {
            return function () {
            infowindow.setContent(addresses[x][0]);
            infowindow.open(map,marker);

            };
          })(marker, x));
        });
      }
    }
  });
}

google.maps.event.addDomListener(window, 'load', initialize);
AndrewRMillar
  • 608
  • 1
  • 7
  • 17
willienels
  • 81
  • 2
  • 9
  • Why are you using the [Geocoding API (meant for server side use)](https://developers.google.com/maps/documentation/geocoding/intro) rather than the [Google Maps Javascript API v3 Geocoder](https://developers.google.com/maps/documentation/javascript/geocoding)? – geocodezip Jul 16 '15 at 00:59
  • Didn't realize the difference. I was using a code snippet from another Stackoverflow answer. I read up on the difference and have since changed to using the Javascript API. Thanks for pointing that out. – willienels Jul 21 '15 at 17:44

1 Answers1

2

The geocoder is asynchronous. Inside the callback function, x == addresses.length. You are using function closure to capture its value for the infowindow, you need to do the same for instantiating the marker.

//This is the problem area:
for (x = 0; x < addresses.length; x++) {
    jQuery.getJSON('http://maps.googleapis.com/maps/api/geocode/json?address='+addresses[x][2]+'&sensor=false', null, function (data) {
        console.log(x); // logs the length of array, 4, every time
        var p = data.results[0].geometry.location;
        var latlng = new google.maps.LatLng(p.lat, p.lng);
        createMarker(latlng, x);
    });
}
function createMarker(latlng, x) {
    marker = new google.maps.Marker({
        position: latlng,
        map: map,
        title: addresses[x][0]
    });
    google.maps.event.addListener(marker, 'click', (function(marker, x) {
        return function () {
          infowindow.setContent(addresses[x][0]);
          infowindow.open(map,marker);

        };
    })(marker, x));
}
geocodezip
  • 158,664
  • 13
  • 220
  • 245
  • 1
    This didn't work, but I was able to refactor my code using one of your other answer posts here: http://stackoverflow.com/questions/29463131/mapping-multiple-locations-with-google-maps-javascript-api-v3-and-geocoding-api?rq=1. Thanks for taking the time to answer these Google Maps questions geocodezip! – willienels Jul 21 '15 at 17:47