2011-12-26 11 views
5

लौटा रहा है मेरे पास जावास्क्रिप्ट में चलने वाला लूप है। इस लूप में मैं एक सूची आइटम बना रहा हूं और इसे एक क्लिक ईवेंट बाध्य कर रहा हूं। जब मैं इस सूची आइटम पर क्लिक करता हूं, तो मैं चाहता हूं कि यह वर्तमान लूप ऑब्जेक्ट से पैरामीटर के रूप में डेटा के साथ एक फ़ंक्शन को कॉल करे।बाइंडेड क्लिक ईवेंट के साथ जावास्क्रिप्ट लूप हमेशा अंतिम परिणाम

समस्या यह है कि कोई भी सूची आइटम मैं क्लिक करता हूं। पैरामीटर के रूप में पारित किया जा रहा डेटा उस ऑब्जेक्ट का अंतिम तत्व है जिसे मैं क्लिक किए जा रहे वर्तमान की बजाय लूपिंग कर रहा हूं।

for(e in data) { 

    var suggestItem = $('<li>'+ data[e]['name'] +'</li>'); 

    suggestItem.click(function() { 
     $(this).addClass('activeSuggestion'); 
     suggestSelect(suggestField, data[e]);  
    }); 

    suggestList.append(suggestItem); 

} 

मुझे लगता है कि मैं समझता हूं कि ऐसा क्यों होता है लेकिन यह सुनिश्चित नहीं है कि मुझे इसे कैसे संभालना चाहिए।

+1

लूप में बनाए गए [jQuery इवेंट हैंडलर का संभावित डुप्लिकेट] (http://stackoverflow.com/questions/7774636/jquery-event-handler-created-in-loop) – Pointy

उत्तर

3

आपको e पर बंद करने की आवश्यकता है।

चूंकि आप jQuery का उपयोग कर रहे हैं, तो सबसे आसान तरीका e के वर्तमान मूल्य को jQuery के data फ़ंक्शन के साथ सहेजना होगा। चूंकि जावास्क्रिप्ट में सभी फ़ंक्शन पैरामीटर मूल्य से पारित होते हैं, इसलिए यह प्रभावी रूप से बंद हो जाता है; अब आपके क्लिक हैंडलर e के मान के साथ काम करेंगे जब हैंडलर बनाया गया था, और जब लूप समाप्त होता है तो e मान नहीं रखता है।

for(e in data) { 

    var suggestItem = $('<li>'+ data[e]['name'] +'</li>'); 

    suggestItem.data('savedE', e).click(function() { 
     $(this).addClass('activeSuggestion'); 
     suggestSelect(suggestField, data[$(this).data('savedE')]); 
    }); 

    suggestList.append(suggestItem); 

} 
+0

यह चाल है। धन्यवाद –

+0

@ जस्टिन कार्ल्सन - मेरी खुशी - शुभकामनाएँ! –

5

यह एक क्लासिक जावास्क्रिप्ट बंद प्रश्न है। जब क्लिक इवेंट ट्रिगर होता है (जब आप किसी चीज़ पर क्लिक करते हैं), लूप पहले ही निष्पादन समाप्त कर चुका है। e का मान जो भी data में अंतिम कुंजी है। समस्या का समाधान अपने लूप के अंदर एक नया दायरा बनाना है।

for(var e in data) { 
    (function(datum) { 
     suggestList.append(
      $('<li>' + datum.name + '</li>') 
      .click(function() { 
       $(this).addClass('activeSuggestion'); 
       suggestSelect(suggestField, datum);  
      }); 
     ); 
    })(data[e]); 
} 

जावास्क्रिप्ट फ़ंक्शन स्कॉप्ड है, इसलिए जब भी कोई नया फ़ंक्शन सामना होता है, तो एक नया दायरा बनाया जाता है। उपरोक्त कोड data[e] का मान datum में मानता है क्योंकि यह इसे फ़ंक्शन के पैरामीटर के रूप में पास करता है। जो कम भ्रमित हो सकता है यह कोड करने के लिए एक और तरीका है:

for(var e in data) { 
    (function() { 
     var datum = data[e]; 
     suggestList.append(
      $('<li>' + datum.name + '</li>') 
      .click(function() { 
       $(this).addClass('activeSuggestion'); 
       suggestSelect(suggestField, datum);  
      }); 
     ); 
    })(); 
} 

यह कार्य करने के लिए एक पैरामीटर में पारित नहीं है, लेकिन समारोह scoped, हर बार क्लिक करें घटना यह जहां datum के लिए दिखेगा शुरू हो रहा है क्योंकि जावास्क्रिप्ट है सौंपा गया था।

कृपया for(VAR e in data) पर ध्यान दें जो e को वैश्विक चर बनने से रोक देगा।

संबंधित मुद्दे