google map api со ссылками на мультимаркеры

я использовал это: маркер Google Maps как ссылка API v3

что я получил, так это то, что все маркеры на моей карте имеют одну и ту же ссылку, поэтому я немного изменил код, и ничего не помогло.

главное, с чем я борюсь, это то, что в первом цикле for переменная i находится в диапазоне от 0 до n, но внутри функции geocoder.gercode это всегда значение n (верхнее значение), а не увеличение от 0 до n и поэтому моя ссылка всегда последняя

var AllPlaces = new Array();
var address = [<%=LocationStr%>];
var links = [<%=LinkStr%>];
var dolinks = (links.length == 0) ? false : true;
var MaxAddress = address.length;
var ThisLink;
var Markers = new Array();
var Mj = 0;
var geocoder;
function initialize() {
    geocoder = new google.maps.Geocoder();
    for (var i = 0; i < MaxAddress; i++) {
        ThisLink = "";
        Mj = i;
        if (dolinks) {
            ThisLink = links[i];
        }
        geocoder.geocode( { 'address': address[i]}, function(results, status) {
            if (status == google.maps.GeocoderStatus.OK) {
                AllPlaces.push(results[0].geometry.location);
                if (MaxAddress == 1) {
                    map.setCenter(results[0].geometry.location);
                }
                else {
                    DoCenter(AllPlaces,map);
                }
                Markers[i] = new google.maps.Marker({
                    map: map,
                    url: ThisLink, 
                    position: results[0].geometry.location
                });
                alert(Mj);
                if (dolinks) {
                    google.maps.event.addListener(Markers[i], 'click', function() {
                        window.location.href = Markers[i].url;
                    });
                }
            }
        });
    }
    var latlng = new google.maps.LatLng();
    var myOptions = {
        zoom: <%=ZoomStr%>,
        mapTypeControl: false,
        streetViewControl: false,
        panControl: false,
        zoomControl: true,
        scaleControl: false,
        mapTypeId: google.maps.MapTypeId.ROADMAP
    }; 
    var map = new google.maps.Map(document.getElementById("<%=DivID%>"), myOptions);
    }

    function DoCenter(LL,obj) {
        if (LL.length < MaxAddress) return;
        var bounds = new google.maps.LatLngBounds ();
        for (var i = 0, LtLgLen = LL.length; i < LtLgLen; i++) {
            bounds.extend (LL[i]);
        }
        obj.fitBounds (bounds);
}

person Y.G.J    schedule 19.10.2011    source источник


Ответы (2)


Просто уточнить в чем проблема. Ваш i растет, но, как вы знаете, этот i живой. т.е. пока вы зацикливаетесь, его значение также меняется. Так, например:

var arr = [];
for(var i=0; i<5; i++) {
   var func = function() {
      console.log(i);
   }
   arr.push(func);
}

for(var j=0; j<5; j++) {
    arr[j]();
}

Результат приведенного выше кода:

5
5
5
5
5

Решение состоит в том, чтобы создать анонимную функцию и немедленно вызвать ее:

var arr = [];
for(var i=0; i<5; i++) {
    var func = function(index) {
        return function() {
            console.log(index);
        }
    }(i);
    arr.push(func);
}
for(var j=0; j<5; j++) {
    arr[j]();
}
person Krasimir    schedule 19.10.2011
comment
не могли бы вы объяснить больше об этом? - person Y.G.J; 19.10.2011
comment
Да, извините, я только что исправил свой код. Сейчас я должен идти. Но когда я вернусь, добавлю дополнительный комментарий относительно подхода. - person Krasimir; 19.10.2011
comment
спасибо - мне удалось исправить свой код с помощью этого и некоторых других примеров, которые я нашел - person Y.G.J; 19.10.2011

geocoder.geocode запускается асинхронно. ваш цикл for может завершиться до выполнения первого обратного вызова геокодирования. Создайте новую функцию, чтобы связать каждую ссылку. Примечание. Каждая функция запускается в новом контексте. Модифицированный код:

var AllPlaces = new Array();
var address = [<%=LocationStr%>];
var links = [<%=LinkStr%>];
var dolinks = (links.length == 0) ? false : true;
var MaxAddress = address.length;
var ThisLink;
var Markers = new Array();
var Mj = 0;
var geocoder;
function reversGeoCord(address, ThisLink ){

   geocoder = new google.maps.Geocoder();
   geocoder.geocode( { 'address': address}, function(results, status) {
            if (status == google.maps.GeocoderStatus.OK) {
                AllPlaces.push(results[0].geometry.location);
                if (MaxAddress == 1) {
                    map.setCenter(results[0].geometry.location);
                }
                else {
                    DoCenter(AllPlaces,map);
                }
                Markers[i] = new google.maps.Marker({
                    map: map,
                    url: ThisLink, 
                    position: results[0].geometry.location
                });
                alert(Mj);
                if (dolinks) {
                    google.maps.event.addListener(Markers[i], 'click', function() {
                        window.location.href = Markers[i].url;
                    });
                }
            }
        });
}
function initialize() {

    for (var i = 0; i < MaxAddress; i++) {
        ThisLink = "";
        Mj = i;
        if (dolinks) {
            ThisLink = links[i];
        }
        reversGeoCord(address[i], ThisLink  );
    }
    var latlng = new google.maps.LatLng();
    var myOptions = {
        zoom: <%=ZoomStr%>,
        mapTypeControl: false,
        streetViewControl: false,
        panControl: false,
        zoomControl: true,
        scaleControl: false,
        mapTypeId: google.maps.MapTypeId.ROADMAP
    }; 
    var map = new google.maps.Map(document.getElementById("<%=DivID%>"), myOptions);
    }

    function DoCenter(LL,obj) {
        if (LL.length < MaxAddress) return;
        var bounds = new google.maps.LatLngBounds ();
        for (var i = 0, LtLgLen = LL.length; i < LtLgLen; i++) {
            bounds.extend (LL[i]);
        }
        obj.fitBounds (bounds);
}
person Anoop    schedule 19.10.2011