दिलचस्प पोस्ट
वेबवेव में स्थानीय एसएफएफ फाइलें कैसे खेलेंगी JQuery में ईवेंट हैंडलर्स को मैं तर्क कैसे दे सकता हूं? गतिशील रूप से एक स्थानीय चर बनाने के लिए कैसे? आयात करें psycopg2 लाइब्रेरी लोड नहीं है: libssl.1.0.0.dylib क्यों चर नाम अक्सर 'एम' पत्र के साथ शुरू करते हैं? कोणीय UI- राउटर कैसे एक "लेआउट" स्थिति बनाने के लिए? क्या मुझे दो "कहां" खंड या "और" मेरे LINQ क्वेरी में उपयोग करना चाहिए? HTML में एक ऑब्जेक्ट टैग पर डेटा सामग्री बदलना एक तालिका में माइक्रोसॉफ्ट एक्सेस एक से अधिक पंक्तियां एकत्रित करता है एक बार में JSON सरणी स्ट्रीम को एक आइटम अवश्य दें जब तक यह पूरी तरह तैयार नहीं होता है तब तक खिड़की को प्रदर्शित करने से रोकना? स्काला में नाम से कॉल बनाम कॉल करके कॉल करें, स्पष्टीकरण की आवश्यकता है फ़ोकस पर और क्लिक पर ListView आइटम का रंग कैसे परिवर्तित करें दो तिथियों के बीच डेटाफ़्रेम पंक्तियां चुनें त्रुटि: कोणीय नियंत्रक से

AddEventListener का उपयोग कर हेन्डलर के भीतर "यह" का मान

मैंने प्रोटोटाइप के माध्यम से एक जावास्क्रिप्ट ऑब्जेक्ट बनाया है मैं एक तालिका गतिशील रूप से प्रस्तुत करने की कोशिश कर रहा हूं जबकि रेंडरिंग भाग सरल है और ठीक काम करता है, मुझे गतिशील रूप से रेंडर किए गए तालिका के लिए कुछ क्लाइंट साइड इवेंट्स को भी संभालना होगा। वह भी आसान है। जहां मुझे समस्या हो रही है, उस समारोह के अंदर "यह" संदर्भ के साथ होता है जो ईवेंट को संभालता है I इसके बजाय "यह" ऑब्जेक्ट का संदर्भ देता है, यह उस तत्व को संदर्भित करता है जो ईवेंट को उठाया।

कोड देखें समस्याग्रस्त क्षेत्र "टिकटटैबल.प्रोतिटिपहैंडलेसेलक्लिक = समारोह ()" में है

function ticketTable(ticks) { // tickets is an array this.tickets = ticks; } ticketTable.prototype.render = function(element) { var tbl = document.createElement("table"); for ( var i = 0; i < this.tickets.length; i++ ) { // create row and cells var row = document.createElement("tr"); var cell1 = document.createElement("td"); var cell2 = document.createElement("td"); // add text to the cells cell1.appendChild(document.createTextNode(i)); cell2.appendChild(document.createTextNode(this.tickets[i])); // handle clicks to the first cell. // FYI, this only works in FF, need a little more code for IE cell1.addEventListener("click", this.handleCellClick, false); // add cells to row row.appendChild(cell1); row.appendChild(cell2); // add row to table tbl.appendChild(row); } // Add table to the page element.appendChild(tbl); } ticketTable.prototype.handleCellClick = function() { // PROBLEM!!! in the context of this function, // when used to handle an event, // "this" is the element that triggered the event. // this works fine alert(this.innerHTML); // this does not. I can't seem to figure out the syntax to access the array in the object. alert(this.tickets.length); } 

वेब के समाधान से एकत्रित समाधान "AddEventListener का उपयोग कर हेन्डलर के भीतर "यह" का मान"

आपको अपने उदाहरण के लिए "बाइंड" हैंडलर चाहिए

 var _this = this; function onClickBound(e) { _this.handleCellClick.call(cell1, e || window.event); } if (cell1.addEventListener) { cell1.addEventListener("click", onClickBound, false); } else if (cell1.attachEvent) { cell1.attachEvent("onclick", onClickBound); } 

ध्यान दें कि ईवेंट हैंडलर event ऑब्जेक्ट (पहले तर्क के रूप में पारित) को handleCellClick और एक उचित संदर्भ में handleCellClick को handleCellClick है (यानी किसी तत्व को संदर्भित करना जो कि ईवेंट श्रोता को संलग्न किया गया था)।

यह भी ध्यान दें कि संदर्भ सामान्यकरण यहां है (यानी ईवेंट हैंडलर में this उचित सेटिंग) ईवेंट हेन्डलर ( onClickBound ) और एक तत्व ऑब्जेक्ट ( onClickBound ) के रूप में उपयोग किए जाने वाले फ़ंक्शन के बीच एक परिपत्र संदर्भ बनाता है। आईई (6 और 7) के कुछ संस्करणों में यह संभवतः मेमोरी रिसाव का परिणाम देगा। सार में यह रिसाव ब्राउज़र के कारण देशी और मेजबान ऑब्जेक्ट के बीच परिपत्र संदर्भ के कारण पृष्ठ ताज़ा पर स्मृति को रिलीज़ करने में असफल रहा है।

इसे निगराने के लिए, आपको या तो this सामान्य करने की आवश्यकता होगी; बी) वैकल्पिक (और अधिक जटिल) सामान्यीकरण रणनीति को रोजगार; ग) पेज अनलोड पर मौजूदा इवेंट श्रोताओं को "क्लीन अप" करें, या तो detachEvent removeEventListener का उपयोग removeEventListener , detachEvent और एलीमेंट्स detachEvent आईएनजी (जो कि दुर्भाग्य से ब्राउज़र की तेजी से इतिहास नेविगेशन को बेकार कर देगा) का उपयोग कर।

आपको जेएस लाइब्रेरी भी मिल सकती है जो इस का ख्याल रखती है। उनमें से ज्यादातर (उदाहरण: jQuery, प्रोटोटाइप। जेएस, वाईयूआई, आदि) आमतौर पर साफ-सफाई को संभालते हैं (सी) में वर्णित हैं।

आप बाइंड का उपयोग कर सकते हैं जो आपको उस मान को निर्दिष्ट करने देता है जो कि किसी दिए गए फ़ंक्शन के सभी कॉल्स के लिए इसका उपयोग किया जाना चाहिए।

  var Something = function(element) { this.name = 'Something Good'; this.onclick1 = function(event) { console.log(this.name); // undefined, as this is the element }; this.onclick2 = function(event) { console.log(this.name); // 'Something Good', as this is the binded Something object }; element.addEventListener('click', this.onclick1, false); element.addEventListener('click', this.onclick2.bind(this), false); // Trick } 

उपरोक्त उदाहरण में एक समस्या यह है कि आप श्रोता को बाइंड से नहीं हटा सकते। किसी भी घटना को पकड़ने के लिए एक अन्य समाधान handleEvent नामक एक विशेष समारोह का उपयोग कर रहा है:

 var Something = function(element) { this.name = 'Something Good'; this.handleEvent = function(event) { console.log(this.name); // 'Something Good', as this is the Something object switch(event.type) { case 'click': // some code here... break; case 'dblclick': // some code here... break; } }; // Note that the listeners in this case are this, not this.handleEvent element.addEventListener('click', this, false); element.addEventListener('dblclick', this, false); // You can properly remove the listners element.removeEventListener('click', this, false); element.removeEventListener('dblclick', this, false); } 

हमेशा की तरह एमडीएन सबसे अच्छा है 🙂 मैं सिर्फ इस सवाल का जवाब देने की तुलना में हिस्सा चिपकाता है।

साथ ही, EventListener इंटरफ़ेस का उपयोग करने के लिए एक और तरीका है (DOM2 !!) यह सोचकर कि कोई भी इसका उल्लेख नहीं करता है, यह सोचकर कि यह सबसे बेहतर तरीका है और ऐसी स्थिति के लिए है।

यानी, एक कॉलबैक फ़ंक्शन गुजरने के बजाय, आप एक ऑब्जेक्ट पास करते हैं जो EventListener इंटरफ़ेस लागू करता है। सीधे शब्दों में कहें, इसका मतलब है कि आपके पास "handleEvent" नामक ऑब्जेक्ट में एक संपत्ति होनी चाहिए, जो ईवेंट हैंडलर फ़ंक्शन को इंगित करता है। फ़ंक्शन के अंदर मुख्य अंतर यह है, this addEventListener पास ऑब्जेक्ट को संदर्भित करेगा। यही है, यह। this.theTicketTable नीचे दिए गए ऑब्जेक्ट उदाहरण होगा। मैं क्या समझता हूं, संशोधित कोड को सावधानी से देखें:

 ticketTable.prototype.render = function(element) { ... var self = this; /* * Notice that Instead of a function, we pass an object. * It has "handleEvent" property/key. You can add other * objects inside the object. The whole object will become * "this" when the function gets called. */ cell1.addEventListener('click', { handleEvent:this.handleCellClick, theTicketTable:this }, false); ... }; // note the "event" parameter added. ticketTable.prototype.handleCellClick = function(event) { /* * "this" does not always refer to the event target element. * It is a bad practice to use 'this' to refer to event targets * inside event handlers. Always use event.target or some property * from 'event' object passed as parameter by the DOM engine. */ alert(event.target.innerHTML); // "this" now points to the object we passed to addEventListener. So: alert(this.theTicketTable.tickets.length); } 

मुझे पता है कि यह एक पुरानी पोस्ट है, लेकिन आप संदर्भ को केवल एक चर self लिए निर्दिष्ट कर सकते हैं, अपने फ़ंक्शन को किसी गुमनाम समारोह में फेंक सकते हैं जो आपके फ़ंक्शन को। .call(self) साथ .call(self) और संदर्भ में गुजरता है।

 ticketTable.prototype.render = function(element) { ... var self = this; cell1.addEventListener('click', function(evt) { self.handleCellClick.call(self, evt) }, false); ... }; 

यह "स्वीकार किए जाते हैं उत्तर" से बेहतर काम करता है क्योंकि संदर्भ को पूरे वर्ग या वैश्विक के लिए एक वैरिएबल निर्दिष्ट करने की आवश्यकता नहीं होती है, बल्कि यह एक ही तरीके से इस घटना के लिए सुनता है।

कामथलीन और गैगरीन के उत्तर से भारी प्रभाव पड़ा मैंने सोचा कि मैं इससे निपट सकता हूं।

मैं सोच रहा था कि यदि आप एक कॉलबैक सूची में handellClell डालते हैं और ईवेंट पर EventListener इंटरफ़ेस का उपयोग करते हुए ऑब्जेक्ट का उपयोग करते हैं, तो संभवत: थोड़ी अधिक स्वतंत्रता प्राप्त कर सकते हैं और कॉलबैक सूची विधियों को इस सही के साथ ट्रिगर करने के लिए।

 function ticketTable(ticks) { // tickets is an array this.tickets = ticks; // the callback array of methods to be run when // event is triggered this._callbacks = {handleCellClick:[this._handleCellClick]}; // assigned eventListenerInterface to one of this // objects properties this.handleCellClick = new eventListenerInterface(this,'handleCellClick'); } //set when eventListenerInterface is instantiated function eventListenerInterface(parent, callback_type) { this.parent = parent; this.callback_type = callback_type; } //run when event is triggered eventListenerInterface.prototype.handleEvent(evt) { for ( var i = 0; i < this.parent._callbacks[this.callback_type].length; i++ ) { //run the callback method here, with this.parent as //this and evt as the first argument to the method this.parent._callbacks[this.callback_type][i].call(this.parent, evt); } } ticketTable.prototype.render = function(element) { /* your code*/ { /* your code*/ //the way the event is attached looks the same cell1.addEventListener("click", this.handleCellClick, false); /* your code*/ } /* your code*/ } //handleCellClick renamed to _handleCellClick //and added evt attribute ticketTable.prototype._handleCellClick = function(evt) { // this shouldn't work alert(this.innerHTML); // this however might work alert(evt.target.innerHTML); // this should work alert(this.tickets.length); } 

व्हाट अबाउट

 ... cell1.addEventListener("click", this.handleCellClick.bind(this)); ... ticketTable.prototype.handleCellClick = function(e) { alert(e.currnetTarget.innerHTML); alert(this.tickets.length); } 

e.currnetTarget लक्ष्य को इंगित करता है जो कि "इवेंट" पर बाइट है ( इवेंट को उठाए जाने वाले तत्व)

बाँध (यह) क्लिक कार्यक्रम समारोह के अंदर "यह" के आउटर्सस्कॉप मान को संरक्षित करता है।

यदि आप चाहते हैं कि सटीक लक्ष्य पर क्लिक करने के बजाय e.target का उपयोग किया जाए