如何使用jQuery触发类更改事件?

Mat*_*eil 63 javascript jquery javascript-events

我希望有类似的东西:

$('#myDiv').bind('class "submission ok" added'){
    alert('class "submission ok" has been added');
});
Run Code Online (Sandbox Code Playgroud)

Ror*_*san 133

当课程发生变化时,不会引发任何事件.另一种方法是在以编程方式更改类时手动引发事件:

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

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

UPDATE

这个问题似乎是在收集一些访问者,所以这里有一个方法的更新,无需使用新的修改现有代码就可以使用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');
Run Code Online (Sandbox Code Playgroud)
.red { color: #C00; }
Run Code Online (Sandbox Code Playgroud)
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="foo" class="bar">#foo.bar</div>
Run Code Online (Sandbox Code Playgroud)

请注意,MutationObserver它仅适用于较新的浏览器,特别是Chrome 26,FF 14,IE 11,Opera 15和Safari 6.有关详细信息,请参阅MDN.如果您需要支持旧版浏览器,那么您需要使用我在第一个示例中概述的方法.

  • @Benj,这与我原来的答案相同(即使用“trigger()”),但请注意,由于使用“bind()”,它已经非常过时了。但我不确定它是如何“完成”任何事情的 (2认同)
  • 这是该解决方案的改进形式,带有过滤器/sf/answers/2948525681/ (2认同)

Nic*_*ook 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);
Run Code Online (Sandbox Code Playgroud)

然后你的其余代码就像你期望的那样简单.

$(selector).on('classChanged', function(){ /*...*/ });
Run Code Online (Sandbox Code Playgroud)

更新:

这种方法确实假设只能通过jQuery addClass和removeClass方法更改类.如果以其他方式修改类(例如通过DOM元素直接操作类属性),则需要使用类似于MutationObservers的内容,如此处接受的答案中所述.

此外,作为这些方法的一些改进:

  • 每个被添加(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);
    
    Run Code Online (Sandbox Code Playgroud)

使用这些替换函数,您可以通过检查回调函数的参数来处理通过classChanged更改的任何类或添加或删除的特定类:

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


Sat*_*ngh 7

trigger火自己的事件.什么时候更改类添加触发器的名称

JS Fiddle DEMO

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

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

    alert("Red bg set ");
});
Run Code Online (Sandbox Code Playgroud)

学习jQuery:简单易用的jQuery教程博客