为什么if和else都会在滚动时执行?

时间:2015-06-21 14:05:27

标签: jquery angularjs scroll angular-directive

对于我的滚动事件,我得到了这个非常奇怪的行为,我似乎无法弄清楚为什么会发生这种情况或者如何修复它。基本上我所拥有的是一个侦听滚动的事件监听器,但if和else都是在滚动时执行的。

我得到了这个指令:

core.directive('offsetColor', [function() {

  return {
    restrict: 'A',
    link: function(scope, element, attrs) {

      $window.on('scroll', function() {
        var windowY = $(window).scrollTop();
        var elementY = element.offset().top - 60; // -60 to add site header height

        if (elementY <= windowY) {
          console.log('element is at top');
        }
        else {
          console.log('no element is at top');
        }
      });
    }
  }
}]);

任务是根据某些元素的y位置更改网站标题的颜色。

目前我已将此指令设置为两个元素。

现在我简单地猜测为什么会发生这种情况是因为我在两个元素而不是一个上设置了指令,因此滚动事件“循环”通过两者元素和检查他们的y位置。因此,其中一个元素位于顶部,但另一个元素不是,导致ifelse被执行。

我觉得我已经尝试了一切来阻止它执行两者但我没有解决方案。

我在这里做错了什么?

1 个答案:

答案 0 :(得分:0)

正如Roamer-1888在评论中提到的,为了解决这样的问题,你需要整合你的事件处理程序(在这种情况下是滚动侦听器)。

这里有一个想法:创建一个指令并将其应用于所有改变标题颜色的元素的共同祖先。在此指令内的窗口中添加滚动侦听器。

现在,无论是通过使用jQuery,还是使用与父指令(like the AngularJS tabs example)对话的子指令,循环遍历可能会改变标题颜色的所有元素。从窗口位置抓取它们的偏移量,然后找到偏移量最小的那个。

具有最小偏移量的元素是应该影响标题颜色的元素。

总而言之,你的指令看起来像这样(进入jQuery路由;嵌套指令路由留作读取的练习)(未经测试):

core.directive('offsetColorContainer', [function() {

  return {
    restrict: 'A',
    link: function(scope, element, attrs) {
      var colorElems = $('.some-selector-that-identifies-your-color-elems', element);

      $window.on('scroll', function() {
        var windowY = $(window).scrollTop(),
            closestElem = null,
            closestDist = null;

        colorElems.each(function() {
          var elem = $(this),
              elemDist = Math.abs(elem.offset().top - windowY);

          if (closestElem === null || elemDist < closestDist)
          {
            closestElem = elem;
            closestDist = elemDist;
          }
        });

        if (closestElem !== null)
        {
          // change the header color based on closestElem
        }
      });
    }
  }
}]);

请注意,您可能需要调整元素距离逻辑,具体取决于元素实际代表的内容,但这应该让您从正确的方向开始。