2008-12-11 6 views
9

J'ai une question similaire à celle-ci: Event handlers inside a Javascript loop - need a closure? mais j'utilise jQuery et la solution donnée semble déclencher l'événement quand il est lié plutôt que sur un clic.jQuery Fermetures, boucles et événements

Voici mon code:

for(var i in DisplayGlobals.Indicators) 
{ 
    var div = d.createElement("div"); 
    div.style.width = "100%"; 
    td.appendChild(div); 

    for(var j = 0;j<3;j++) 
    { 
     var test = j; 
     if(DisplayGlobals.Indicators[i][j].length > 0) 
     { 
      var img = d.createElement("img"); 
      jQuery(img).attr({ 
        src : DisplayGlobals.Indicators[i][j], 
        alt : i, 
        className: "IndicatorImage" 
       }).click(
        function(indGroup,indValue){ 
         jQuery(".IndicatorImage").removeClass("active"); 
         _this.Indicator.TrueImage = DisplayGlobals.Indicators[indGroup][indValue]; 
         _this.Indicator.FalseImage = DisplayGlobals.IndicatorsSpecial["BlankSmall"]; 
         jQuery(this).addClass("active"); 
        }(i,j) 
       ); 
       div.appendChild(img); 
      } 
    } 
} 

J'ai essayé deux différentes façons sans succès ...

Le problème initial était que _this.Indicator.TrueImage était toujours la dernière valeur parce que je utilisait les compteurs de boucle plutôt que les paramètres pour choisir la bonne image.

Répondre

14

Il vous manque une fonction. La fonction .cliquez a besoin d'une fonction en tant que paramètre de sorte que vous devez faire ceci:

.click(
    function(indGroup,indValue) 
    { 
     return function() 
     { 
      jQuery(".IndicatorImage").removeClass("active"); 
      _this.Indicator.TrueImage = DisplayGlobals.Indicators[indGroup][indValue]; 
      _this.Indicator.FalseImage = DisplayGlobals.IndicatorsSpecial["BlankSmall"]; 
      jQuery(this).addClass("active"); 
     } 
    }(i,j); 
); 
+1

Merci :) Sentez-vous une peu bête maintenant! –

13

Solution par Greg est toujours valide, mais vous pouvez le faire sans créer de fermeture supplémentaire maintenant, en utilisant eventData paramètre de jQuery click méthode (ou bind ou toute autre méthode de liaison d'événement, d'ailleurs). Il semble beaucoup plus simple et probablement plus efficace (une fermeture de moins par itération).

La documentation de la méthode bind comporte une description et quelques exemples de données d'événement.

6

La réponse de Nikita fonctionne très bien tant que vous utilisez jQuery 1.4.3 et versions ultérieures. Pour les versions antérieures à ce (retour à 1.0) vous devrez utiliser bind comme suit:

.bind('click', {indGroup: i, indValue : j}, function(event) { 
    alert(event.data.indGroup); 
    alert(event.data.indValue); 
    ... 
}); 

Hope this helps quelqu'un d'autre encore en utilisant 1.4.2 (comme moi)