如何在单击时阻止jQuery mouseenter / mouseleave事件

时间:2011-11-28 23:47:23

标签: jquery

我有一种感觉,我可能会以完全错误的方式解决这个问题......希望有人可以帮助我。

我为我的应用程序开发了一个星级系统。

以下是我到目前为止执行以下操作的代码:

显示单个星号,其中包含一个数字,通过JSON从数据库中检索。当你将鼠标悬停在这颗恒星上时,10颗恒星会褪色。当你点击它然后初始化'投票'模式和mouseenter,mouseleave事件处理程序被分配给各个星。当你点击一个星星时,会发一个更新数据库的ajax帖子,替换编号星号中的数字(平均投票得分)并将一个类别添加到相关的星数中,这样就可以直观地表示星级评分这个项目。一切正常。

问题: -

目前,当您点击一次进入“投票”模式然后悬停在星星上(在鼠标中心时添加突出显示类),然后点击实际投票原始mouseenter / mouseleave事件处理程序仍然存在于各个星星上。< / p>

我希望在用户投票后悬停停止时添加/删除类。

我确定答案将与使用event.stopPropagation解决,将处理程序本身与.off()取消绑定,但我似乎无法使其工作。

有什么想法吗?

//show ratings on hover
$('#full-width-layout_c1_col-1-1_1').on('mouseenter mouseleave click', 
                                        '.rate', 
                                        function (e) {

  $ratings = $(this).parent().find('.ratings_stars');

  if (e.type == 'mouseenter') {
    $ratings.fadeIn();
  }

  if (e.type == 'mouseleave') {
    $ratings.fadeOut();
  }

  if (e.type == 'click') {

    $('#full-width-layout_c1_col-1-1_1').on('mouseenter mouseleave click',
                                            '.ratings_stars', 
                                            function (e) {

      var $vote = $(this).parent().find('.vote_info').text();
      var $hover = $(this).prevAll().andSelf();
      var $original = $(this).parent()
                             .find('.star_' + $vote)
                             .prevAll()
                             .andSelf();

      if (e.type == 'mouseenter') {
        $hover.addClass('ratings_over');
        $(this).nextAll().removeClass('ratings_vote');
      }

      if (e.type == 'mouseleave') {
        $hover.andSelf().removeClass('ratings_over');
        $original.addClass('ratings_vote');
      }

      //Highlight stars on hover and insert into database on click
      if (e.type == 'click') {

        var $row = $(this).closest('tr').find('.songnamecolumn');
        var $rating = $(this).index() + 1;
        var $songID = $(this).closest('tr')
                             .find('.songnamecolumn')
                             .attr('alt');

        var $userID = $('#loggedin_user_id').text();

        $.ajax({
          url: "/wp-content/ratings.php",
          type: 'POST',
          data: 'song_id=' 
                + $songID 
                + '&user_id=' 
                + $userID 
                + '&rating=' 
                + $rating,
          success: function () {
            $songid = $songID;

            updateRating($songid, $row, $original);
          }
        });
      }
    });
  }
});

相关的HTML如下:

<div class="rate">
    <div class="star_1 ratings_stars ratings_vote" style="display: none;">
    </div>
    <div class="star_2 ratings_stars ratings_vote" style="display: none;">
    </div>
    <div class="star_3 ratings_stars ratings_vote" style="display: none;">
    </div>
    <div class="star_4 ratings_stars ratings_vote" style="display: none;">
    </div>
    <div class="star_5 ratings_stars ratings_vote" style="display: none;">
    </div>
    <div class="star_6 ratings_stars" style="display: none;">
    </div>
    <div class="star_7 ratings_stars" style="display: none;">
    </div>
    <div class="star_8 ratings_stars" style="display: none;">
    </div>
    <div class="star_9 ratings_stars" style="display: none;">
    </div>
    <div class="star_10 ratings_stars" style="display: none;">
    </div>
    <div class="vote_info">
        5
    </div>
</div>

2 个答案:

答案 0 :(得分:0)

愚蠢的是,我已经找到了解决方案。虽然希望其他人可以提供更优雅的。

我只是设置ajax onsuccess函数,将一个'voted'类添加到父元素,并使用标准if / else检查具有'voted'类的父元素并使用return false;如果是,否则...绑定mouseenter / mouseleave / click功能。

对我来说感觉有点像黑客,我肯定必须有更好的方法。

如果有人能给我一个更好的解决方案,我会留下一段时间作为回答。

谢谢大家。

答案 1 :(得分:0)

如果您使用Id作为选择器,您也可以使用this.off('mouseenter');

文档:http://api.jquery.com/off/

我发现如果您使用更通用的选择器,它不一定有效,除非您还使用第二个参数,它是.on()命令中使用的确切选择器。

但是如果你总是使用唯一的Id作为选择器,这应该可行。请参阅文档链接。

我正在表达你的答案,因为即使使用更通用的选择器,该解决方案也能正常运行。