jQuery单击函数在添加/删除类时出现异常

3
我有两个列表项,当它们被点击时,应该从“.off”更改为“.on”。每次只能有一个元素被“。on”选中,因此当一个已经打开并且另一个被点击时,两个元素都应该从“.off”更改为“.on”反之亦然。如果单击具有“.on”类的列表项,则应将其更改为“.off”。
我的问题是,当点击具有“.on”类的列表项时,它仍会运行点击功能,就好像它具有“.off”类一样。
我的html:
<ul>
    <li><a href="about" class="off">ABOUT</a></li>
    <li><a href="upload" class="off">SUBMIT</a></li>
</ul>

我使用jQuery 1.7.1运行的javascript代码

$('.off').click(function(event) {
    event.preventDefault();
    $(".on").addClass("off").removeClass("on");
    $(this).addClass("on").removeClass("off");
});
$('.on').click(function(event) {
    event.preventDefault();
    $(this).addClass("off").removeClass("on");
});

有人知道这里发生了什么吗?我的代码有问题还是我遇到了某种错误?

http://jsfiddle.net/ZC3CW/6/

5个回答

4
您使用click()绑定事件的选择器是用于选择添加事件处理程序的元素。当处理程序运行时,选择器不会被考虑在内。
您应该寻找更像这样的东西:
$('li').click(function(event) {
    event.preventDefault();

    if ($(this).hasClass('off')) {
        $(".on").addClass("off").removeClass("on");
        $(this).addClass("on").removeClass("off");
    } else { // $(this).hasClass('on');
        $(this).addClass("off").removeClass("on");
    }
});

您可能希望通过为 ulli 添加 class/id 来使 li 选择器更加明确。

更进一步混淆事情的是,如果您使用的是 jQuery > 1.7,您也可以这样做:

$(document).on('click', '.off', function(event) {
    event.preventDefault();
    $(".on").addClass("off").removeClass("on");
    $(this).addClass("on").removeClass("off");
});
$(document).on('click', '.on', function(event) {
    event.preventDefault();
    $(this).addClass("off").removeClass("on");
});

这是因为.on()函数是通过将事件处理程序附加到选择的元素(document)来工作的,如果事件源匹配选择器.off,则只有在指定事件(click)发生时才会执行处理程序(函数),而不是在绑定时。请注意,在事件触发时匹配选择器.off,而非绑定时间。

2
我建议将点击事件添加到另一个选择器上,这应该对你有用...
$("ul li a").click(function(e){
   e.preventDefault();

   if($(this).hasClass("off")){
      $("ul li a").addClass("off").removeClass("on");
      $(this).addClass("on").removeClass("off");
   }
   else{
      $(this).addClass("off").removeClass("on");
   }
});

1
问题在于jQuery处理程序在页面加载时被附加并保持不变,无论更改它们的类别如何。使用on('click', handler)而不是click()。live('click', handler) 编辑:刚注意到.live()在jQuery 1.7中已被弃用。

0
我看到的问题是,您的“on”类在单击事件发生时没有起作用,因此您的 $('.on').click 方法从未被调用。

尝试在更改类后重新分配事件(以下是示例):

var assignClicks = function () {
    $('.off').click(function(event) {
        event.preventDefault();
        $(".on").addClass("off").removeClass("on");
        $(this).addClass("on").removeClass("off");
        assignClicks();
    });
    $('.on').click(function(event) {
        event.preventDefault();
        $(this).addClass("off").removeClass("on");
        assignClicks();
    });
};
assignClicks();

希望这可以帮助到你,
皮特

@pete:附加事件处理程序不会删除任何先前绑定的事件处理程序,因此您最终将绑定一个“on”和“off”事件处理程序。如果您真的想要这种方法,您还需要使用off()/unbind()来删除事件处理程序。 - Matt

0

点击事件绑定到元素而不是类。也许您可以将事件附加到

  • 元素并检测/切换元素的类:
  • $('li').click(function(event) {
        event.preventDefault();
        if( $(this).hasClass('on') ) {
            $(this).removeClass('on');
        }
        else {
            $(this).addClass('on');
            $(this).siblings().removeClass('on');
        }
    });
    

    网页内容由stack overflow 提供, 点击上面的
    可以查看英文原文,
    原文链接