JQuery का उपयोग करके वर्ग परिवर्तन पर किसी घटना को कैसे फायर किया जाए?


जवाबों:


172

जब कोई वर्ग बदलता है तो कोई घटना नहीं होती है। वैकल्पिक रूप से एक घटना को मैन्युअल रूप से उठाना है जब आप प्रोग्राम को कक्षा में बदलते हैं:

$someElement.on('event', function() {
    $('#myDiv').addClass('submission-ok').trigger('classChange');
});

// in another js file, far, far away
$('#myDiv').on('classChange', function() {
     // do stuff
});

अपडेट करें

यह प्रश्न कुछ आगंतुकों को एकत्रित करता हुआ प्रतीत होता है, इसलिए यहां एक दृष्टिकोण के साथ एक अपडेट दिया गया है जिसे नए का उपयोग करके मौजूदा कोड को संशोधित किए बिना उपयोग किया जा सकता है MutationObserver:

var $div = $("#foo");
var observer = new MutationObserver(function(mutations) {
  mutations.forEach(function(mutation) {
    if (mutation.attributeName === "class") {
      var attributeValue = $(mutation.target).prop(mutation.attributeName);
      console.log("Class attribute changed to:", attributeValue);
    }
  });
});
observer.observe($div[0], {
  attributes: true
});

$div.addClass('red');
.red { color: #C00; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="foo" class="bar">#foo.bar</div>

ध्यान रखें कि MutationObserverयह केवल नए ब्राउज़रों के लिए उपलब्ध है, विशेष रूप से Chrome 26, FF 14, IE 11, Opera 15 और Safari 6. अधिक विवरण के लिए MDN देखें। यदि आपको विरासत ब्राउज़रों का समर्थन करने की आवश्यकता है, तो आपको मेरे पहले उदाहरण में बताई गई विधि का उपयोग करने की आवश्यकता होगी।


इस उत्तर के पूरा होने पर, मैंने यह पाया: stackoverflow.com/a/1950052/1579667
बेंज

1
@Benj यह मेरे मूल उत्तर के रूप में ही है (यानी का उपयोग करते हुए trigger()) हालांकि ध्यान दें कि यह उपयोग के कारण बहुत पुराना है bind()। मुझे यकीन नहीं है कि यह कुछ भी कैसे 'पूरा' करता है, हालांकि
रोरी मैकक्रॉन

मेरे मामले में मुझे एक घटना में आग लगाने की ज़रूरत थी जब एक डोम नोड में MutationObserverमेरे लिए एक विशिष्ट वर्ग काम करता है
मारियो

1
इस फिल्टर के साथ इस समाधान का एक बेहतर रूप है stackoverflow.com/a/42121795/12074818
MVDeveloper1

20

आप मूल jQuery addClass और removeClass फ़ंक्शन को अपने स्वयं के साथ बदल सकते हैं जो मूल फ़ंक्शन को कॉल करेंगे और फिर एक कस्टम ईवेंट को ट्रिगर करेंगे। (मूल फ़ंक्शन संदर्भ को शामिल करने के लिए एक स्व-चालान अनाम फ़ंक्शन का उपयोग करना)

(function( func ) {
    $.fn.addClass = function() { // replace the existing function on $.fn
        func.apply( this, arguments ); // invoke the original function
        this.trigger('classChanged'); // trigger the custom event
        return this; // retain jQuery chainability
    }
})($.fn.addClass); // pass the original function as an argument

(function( func ) {
    $.fn.removeClass = function() {
        func.apply( this, arguments );
        this.trigger('classChanged');
        return this;
    }
})($.fn.removeClass);

तब आपका बाकी कोड उतना ही सरल होगा जितना आप अपेक्षा करेंगे।

$(selector).on('classChanged', function(){ /*...*/ });

अपडेट करें:

यह दृष्टिकोण यह धारणा बनाता है कि कक्षाएं केवल jQuery के addClass और removeClass विधियों के माध्यम से बदल दी जाएंगी। यदि वर्गों को अन्य तरीकों से संशोधित किया जाता है (जैसे कि DOM तत्व के माध्यम से वर्ग विशेषता का प्रत्यक्ष हेरफेर) MutationObserverएस कुछ इस तरह से उपयोग किया जाता है जैसा कि यहां स्वीकृत उत्तर में समझाया गया है तो यह आवश्यक होगा।

इन तरीकों में सुधार के रूप में भी:

  • प्रत्येक वर्ग के लिए एक घटना को जोड़ा जा रहा है ( classAdded) या हटाया गया ( classRemoved) विशिष्ट वर्ग के साथ कॉलबैक फ़ंक्शन के तर्क के रूप में पारित किया गया और केवल तभी ट्रिगर किया गया जब विशेष वर्ग को वास्तव में जोड़ा गया था (पहले मौजूद नहीं था) या हटा दिया गया था (पहले मौजूद था)
  • केवल ट्रिगर classChangedअगर किसी भी वर्ग वास्तव में बदल रहे हैं

    (function( func ) {
        $.fn.addClass = function(n) { // replace the existing function on $.fn
            this.each(function(i) { // for each element in the collection
                var $this = $(this); // 'this' is DOM element in this context
                var prevClasses = this.getAttribute('class'); // note its original classes
                var classNames = $.isFunction(n) ? n(i, prevClasses) : n.toString(); // retain function-type argument support
                $.each(classNames.split(/\s+/), function(index, className) { // allow for multiple classes being added
                    if( !$this.hasClass(className) ) { // only when the class is not already present
                        func.call( $this, className ); // invoke the original function to add the class
                        $this.trigger('classAdded', className); // trigger a classAdded event
                    }
                });
                prevClasses != this.getAttribute('class') && $this.trigger('classChanged'); // trigger the classChanged event
            });
            return this; // retain jQuery chainability
        }
    })($.fn.addClass); // pass the original function as an argument
    
    (function( func ) {
        $.fn.removeClass = function(n) {
            this.each(function(i) {
                var $this = $(this);
                var prevClasses = this.getAttribute('class');
                var classNames = $.isFunction(n) ? n(i, prevClasses) : n.toString();
                $.each(classNames.split(/\s+/), function(index, className) {
                    if( $this.hasClass(className) ) {
                        func.call( $this, className );
                        $this.trigger('classRemoved', className);
                    }
                });
                prevClasses != this.getAttribute('class') && $this.trigger('classChanged');
            });
            return this;
        }
    })($.fn.removeClass);
    

इन प्रतिस्थापन कार्यों के साथ आप तब कॉलबैक प्राप्त करने के तर्क को जांचकर क्लास क्लास या विशिष्ट कक्षाओं के माध्यम से बदले गए या हटाए गए किसी भी वर्ग को संभाल सकते हैं:

$(document).on('classAdded', '#myElement', function(event, className) {
    if(className == "something") { /* do something */ }
});

1
यह ठीक काम करता है, लेकिन "बाकी कोड" में ईवेंट हैंडलर को नए तत्वों के लिए बाध्य करने के लिए लक्ष्य चयनकर्ता को सौंप दिया जाना चाहिए $(parent_selector).on('classChanged', target_selector, function(){ /*...*/ });:। मुझे यह देखने के लिए थोड़ा समय दिया कि मेरे गतिशील रूप से बनाए गए तत्वों ने हैंडलर को आग क्यों नहीं दी। जानने के लिए देखें। jquery.com/events/event-delegation
Timm

7

triggerअपने स्वयं के आयोजन में आग लगाने के लिए उपयोग करें । जब भी आप नाम के साथ क्लास ऐड ट्रिगर बदलें

जेएस फिडेल डेमो

$("#main").on('click', function () {
    $("#chld").addClass("bgcolorRed").trigger("cssFontSet");
});

$('#chld').on('cssFontSet', function () {

    alert("Red bg set ");
});

JQuery जानें: सरल और आसान jQuery ट्यूटोरियल ब्लॉग


2

आप इस तरह से कुछ का उपयोग कर सकते हैं:

$(this).addClass('someClass');

$(Selector).trigger('ClassChanged')

$(otherSelector).bind('ClassChanged', data, function(){//stuff });

लेकिन अन्यथा, नहीं, जब कोई वर्ग बदलता है तो किसी घटना को आग लगाने के लिए कोई पूर्वनिर्धारित फ़ंक्शन नहीं होता है।

यहां ट्रिगर्स के बारे में और पढ़ें


1
ईवेंट के हैंडलर में वही आइटम होना चाहिए जो इवेंट को ट्रिगर करता है। $ (this) .addClass ( 'SomeClass'); $ (चयनकर्ता) .trigger ('ClassChanged') // यह एक ही चयनकर्ता $ (Selector) होना चाहिए। bind ('ClassChanged', data, function () {// stuff});
मेको पेरेज़ एस्टेवेज़

3
आप, यहाँ से नकल करता है, तो हाँ है तो अच्छा है, तो आप प्रदान लिंक भी है लगता है stackoverflow.com/questions/1950038/...
सतिंदर सिंह
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.