如果目标元素不存在,滚动事件也会触发吗?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如果目标元素不存在,滚动事件也会触发吗?相关的知识,希望对你有一定的参考价值。

我有一个侧边栏作为子导航并附加一些自定义的javascript来突出显示其内部的navlinks在用户向下滚动部分。我把这个javascript包含在我的主js文件中。侧边栏不包含在每个页面上。对于性能,我想知道,如果附加滚动事件到这个侧边栏也会在没有包含侧边栏的网站上触发,或者在这些网站上忽略了这段脚本?

        // waypoint for fixed sidebar
        $('.tg-desktop__accordionWrapper').waypoint(function (direction) {
            if (direction === 'down') {
                $(this.element).addClass('tg-accordion__sidebar--fixed');
            } else {
                $(this.element).removeClass('tg-accordion__sidebar--fixed');
            }
        });

        // cache the navigation links 
        var $navigationLinks = $('.tg-accordion__sidebarLink');
        // cache (in reversed order) the sections
        var $sections = $($(".tg-accordion__text").get().reverse());

        // map each section id to their corresponding navigation link
        var sectionIdTonavigationLink = {};
        $sections.each(function() {
            var id = $(this).attr('id');
            sectionIdTonavigationLink[id] = $('.tg-accordion__sidebarLink[href=#' + id + ']');
        });

        // throttle function, enforces a minimum time interval
        function throttle(fn, interval) {
            var lastCall, timeoutId;
            return function () {
                var now = new Date().getTime();
                if (lastCall && now < (lastCall + interval) ) {
                    // if we are inside the interval we wait
                    clearTimeout(timeoutId);
                    timeoutId = setTimeout(function () {
                        lastCall = now;
                        fn.call();
                    }, interval - (now - lastCall) );
                } else {
                    // otherwise, we directly call the function 
                    lastCall = now;
                    fn.call();
                }
            };
        }

        function highlightNavigation() {
            // get the current vertical position of the scroll bar
            var scrollPosition = $(window).scrollTop();

            // iterate the sections
            $sections.each(function() {
                var currentSection = $(this);
                // get the position of the section
                var sectionTop = currentSection.offset().top;

                // if the user has scrolled over the top of the section  
                if (scrollPosition >= sectionTop) {
                    // get the section id
                    var id = currentSection.attr('id');
                    // get the corresponding navigation link
                    var $navigationLink = sectionIdTonavigationLink[id];
                    // if the link is not active
                    if (!$navigationLink.hasClass('active')) {
                        // remove .active class from all the links
                        $navigationLinks.removeClass('active');
                        // add .active class to the current link
                        $navigationLink.addClass('active');
                    }
                    // we have found our section, so we return false to exit the each loop
                    return false;
                }
            });
        }

        $(window).scroll( throttle(highlightNavigation,100) );
答案

就目前而言,滚动处理程序无条件地附加,因此是的,即使在侧边栏的缺席中,处理程序也会触发。并且,很可能,由于jQuery的容忍性,没有任何东西会抛出;但如果没有侧栏,就不会发生任何所需的副作用。

当没有侧边栏时,不应该附加滚动处理程序应该非常简单。事实上,似乎问题中的代码都不需要在这些页面上(如果你愿意,那么“站点”)。

我希望这样的事情:

var $navigationLinks = $('.tg-accordion__sidebarLink');

if( $navigationLinks.length > 0 ) {
    $('.tg-desktop__accordionWrapper').waypoint(function(direction) {
        ...
    });

    ...
    ...
    ...

    function throttle(fn, interval) {
        ...
    }

    function highlightNavigation() {
        ...
    }

    $(window).scroll( throttle(highlightNavigation, 100) );
}

当然,如果您有一个单页应用程序(SPA),并且某些内容有侧边栏而有些内容没有,那么这种方法将无效。您可以将滚动处理程序永久保持连接(在某些情况下执行虚拟操作),或者您可以安排将滚动处理程序与内容同步地附加/分离。

以上是关于如果目标元素不存在,滚动事件也会触发吗?的主要内容,如果未能解决你的问题,请参考以下文章

js事件(Event)知识整理

阻止默认事件,事件委托和周期

即使鼠标不移动,D3'Drag'事件也会触发

解决移动端页面滚动后不触发touchend事件

使“scrollLeft”/“scrollTop”更改不触发滚动事件监听器

解决移动端页面滚动后不触发touchend事件