0

Я пытаюсь найти свиток на своей странице с помощью JavaScript. Чтобы я мог изменять классы и атрибуты некоторых элементов, когда пользователь прокручивал определенное количество страниц. Это моя JS функция:Функция вертикальной прокрутки Javascript

function detectScroll() { 
    var header = document.querySelector(".headerOrig"), 
     header_height = getComputedStyle(header).height.split('px')[0], 
     fix_class = "changeColor"; 

    if(window.pageYOffset > header_height) {  
     header.classList.add(fix_class); 
    } 
    if(window.pageYOffset < header_height) { 
     header.classList.remove(fix_class); 
    } 
    var change = window.setInterval(detectScroll, 5000); 
} 

и я зову его, когда страница загружена:

<body onload="detectScroll();"> 

Однако, у меня есть эта проблема - мне нужно, чтобы создать действительно небольшой интервал так, что функция вызывается, и класс немедленно изменяется. НО затем страница замерзает, и все, кроме функции JS, работает очень медленно. Есть ли лучший способ достичь этого в JavaScript?

Спасибо за любые советы/предложения.

+2

Я думаю, что есть OnScroll обработчик событий в JavaScript. Вы пробовали ? –

+1

Существует 'document.addEventListener (" scroll ", function() {console.log (document.body.scrollTop)})'. Это будет намного проще и более гибко, чем ваше решение. – veproza

ответ

2

Вы хотите изменить пару вещей. Во-первых, мы можем использовать onscroll вместо интервала. Но вы также захотите как можно больше кэшировать, чтобы уменьшить количество вычислений в вашем свитке. Более того, вы должны использовать requestAnimationFrame (или просто «debounce» вообще для старых браузеров - см. Ссылку). Это гарантирует, что ваша работа будет выполняться только тогда, когда браузер планирует перекрасить. Например, пока пользователь прокручивает текущее событие прокрутки, может срабатывать десятки раз, но страница только перерисовывает один раз. Вы заботитесь только о том, что одной перекрашивать, и если мы можем не делать работу для других времен X будет все более гладкой:

// Get our header and its height and store them once 
// (This assumes height is not changing with the class change). 
var header = document.querySelector(".headerOrig"); 
var header_height = getComputedStyle(header).height.split('px')[0]; 
var fix_class = "changeColor"; 

// This is a simple boolean we will use to determine if we are 
// waiting to check or not (in between animation frames). 
var waitingtoCheck = false; 

function checkHeaderHeight() { 
    if (window.pageYOffset > header_height) {  
    header.classList.add(fix_class); 
    } 
    if (window.pageYOffset < header_height) { 
    header.classList.remove(fix_class); 
    } 
    // Set waitingtoCheck to false so we will request again 
    // on the next scroll event. 
    waitingtoCheck = false; 
} 

function onWindowScroll() { 
    // If we aren't currently waiting to check on the next 
    // animation frame, then let's request it. 
    if (waitingtoCheck === false) { 
    waitingtoCheck = true; 
    window.requestAnimationFrame(checkHeaderHeight); 
    } 
} 

// Add the window scroll listener 
window.addEventListener("scroll", onWindowScroll); 
+0

Отличный ответ! Я не думал об этом в такой глубине. Благодаря! – puk789

1

использовать onscroll вместо onload, поэтому вам не нужно вызывать функцию с интервалом. Ваша dedectScroll функция будет срабатывать автоматически, когда любой свиток appers, если вы используете onscroll

<body onscroll="detectScroll();"> 
1

Ваша функция добавляет интервал рекурсивно, вы должны добавить слушатель события к событию прокрутки таким образом:

function detectScroll() { 
    var header = document.querySelector(".headerOrig"), 
     header_height = getComputedStyle(header).height.split('px')[0], 
     fix_class = "changeColor"; 

    if(window.pageYOffset > header_height) {  
     header.classList.add(fix_class); 
    } 
    if(window.pageYOffset < header_height) { 
     header.classList.remove(fix_class); 
    } 

} 
window.addEventListener("scroll",detectScroll);