2013-04-25 52 views
1

我有一個節點列表,我將使用raphael對象繪製每個節點。我有以下循環:在點擊在javascript中循環中獲取對象的正確索引

for(var i=0; i<curNodes.length; i++){ 
    var node = curNodes[i]; 
    var obj = paper.rect(node.getX(), node.getY(), node.width, node.getHeight()) 
    .attr({fill:nodes[i].getColor(), "fill-opacity": 0.6}) 
    .click(function(e){ onMouseClicked(i,e); }); 
} 

,我想調用其可以查看與相關聯的一些數據的功能的「i」 curNodes陣列的第i個元素。然而,最後一個'i'傳遞給這個函數。我的功能是:

var onMouseClicked = function(i, event){ 
switch (event.which) { 
    case 1: 
     this.attr({title: curNodes[i].name}); 
     break; 
    } 
} 

如何在調用函數時訪問正確的索引?

+0

參見:http://stackoverflow.com/questions/3572480/please-explain-the-use-of-javascript-closures-in-loops/3572616#3572616 – slebetman 2013-04-25 04:09:46

回答

3

試試這個:

.click((function (i) { 
    return function (e) { 
     onMouseClicked(i,e); 
    }; 
})(i)); 

就像你注意到的i值(或在您的函數中的參數)是從for循環的最後一個索引。這是因爲click事件不會立即發生 - 綁定會發生,但i的值不會被捕獲。在執行click處理程序時(以任何方式觸發click事件時),for循環已完成(很久以前),並且i的值是循環的最終值。您可以像上面那樣用閉包捕獲i的值。

雖然我知道處理另一種方式,在我看來更清潔,是使用:

.click(clickHandler(i)); 

function clickHandler(index) { 
    return function (e) { 
     onMouseClicked(i, e); 
    }; 
} 
2

這是因爲closure變量i的。

for (var i = 0; i < curNodes.length; i++) { 
    (function(i) { 
     var node = curNodes[i]; 
     var obj = paper.rect(node.getX(), node.getY(), node.width, 
       node.getHeight()).attr({ 
        fill : nodes[i].getColor(), 
        "fill-opacity" : 0.6 
       }).click(function(e) { 
        onMouseClicked(i, e); 
       }); 
    })(i); 
}