2012-02-15 87 views
1

我不明白爲什麼setTimeout不能按我的預期工作。setTimeout()和在谷歌地圖上放置標記

我想在不同的時間放下每個標記,而不是全部在同一時間。

粘貼並運行此代碼爲http://jsfiddle.net,然後才能看到有趣的行爲刪除註釋:

 //setTimeout(function() { 
      addMarker(m); 
     //}, i * 500); 

<link href="http://code.google.com/apis/maps/documentation/javascript/examples/default.css" rel="stylesheet" type="text/css" /> 
<script type="text/javascript" src="//maps.googleapis.com/maps/api/js?sensor=false"></script> 
<script type="text/javascript"> 
    var berlin = new google.maps.LatLng(52.520816, 13.410186); 
    var neighborhoods = [ 
    new google.maps.LatLng(52.511467, 13.447179), 
    new google.maps.LatLng(52.549061, 13.422975), 
    new google.maps.LatLng(52.497622, 13.396110), 
    new google.maps.LatLng(52.517683, 13.394393) 
    ]; 
    var map; 
    function initialize() { 
    var mapOptions = { 
     zoom: 12, 
     mapTypeId: google.maps.MapTypeId.ROADMAP, 
     center: berlin 
    }; 
    map = new google.maps.Map(document.getElementById("map_canvas"),mapOptions); 
    } 

    function drop() { 
    var j = 0; 
    for (var i = 0; i < neighborhoods.length; i++) { 
     var m = neighborhoods[i]; 
     //setTimeout(function() { 
      addMarker(m); 
     //}, i * 500); 
    } 
    } 
    function addMarker(m) { 
    new google.maps.Marker({ 
     position: m, 
     map: map, 
     draggable: false, 
     animation: google.maps.Animation.DROP 
    }); 
    } 
</script> 
<body onload="initialize()"> 
<div id="map_canvas" style="width: 500px; height: 400px;">map div</div> 
<button id="drop" onclick="drop()">Drop Markers</button> 
</body> 
+0

爲什麼不把代碼粘貼到jsfiddle中並將鏈接發佈到它? – 2012-02-15 14:00:04

+0

jsfiddle正在遷移服務器,目前任何人都無法保存代碼 – lito 2012-02-15 14:05:55

回答

7

這是因爲超時事件觸發之前的「M」的值已更改長。

您應該將此代碼封裝在閉包中以捕獲m的值。

是這樣的:

for (var i = 0; i < neighborhoods.length; i++) { 
    var m = neighborhoods[i]; 

    (function(n){ 
     setTimeout(function() { 
     addMarker(n); 
    }, i * 500); 
    }(m)); 
} 
2

問題在於你對鄰域和區域設置變量var m = neighborhoods[i]的迭代。在addMarker(m)中使用的m的值被neighborhoods中的最後一個元素所替代,這將導致所有標記在同一個點上下降。

改爲使用以下代碼(JSFiddle)。它遍歷全局計數器,你可以通過一個靜態變量替換,並設置一個區間,而不是一個超時:

var droppedCount = 0; 
    var droppedInterval = null; 

    function drop() { 
    if(droppedCount === neighborhoods.length){ 
     clearInterval(droppedInterval); 
     return; 
    } 
    else if(droppedInterval === null) 
     droppedInterval = setInterval(drop,500); 

    var m = neighborhoods[droppedCount++]; 
    addMarker(m); 
    } 
+0

是的,我明白,價值是不斷(4),但爲什麼?我該如何解決它? – lito 2012-02-15 14:06:58

+1

@lito:我已經更新了我的答案。使用全局或靜態('drop.droppedCount')計數器。 – Zeta 2012-02-15 14:09:30

1

的問題是,在setTimeout的功能關閉在可變米,而不是在創建時間的它的當前值。解決方案應該是:

// ... 
var m = neighborhoods[i]; 
(function (myMarker) { 
setTimeout(function() { 
    addMarker(myMarker); 
}, i * 500); 
}(m)); 
// ...