Animowany Scroll do Kotwicy JS dla Motywu z Edytorem Bloków WordPress (działający na mobile)

Update2

Poprzedni kod przestał mi działać z jakimś updatem, okazało się że offsetTop nie zwracał prawidłowej wartości zostało to zmienione na funckje pomocniczą getOffsetTop która oblicza realną odległość.

function triggerTouchEvent(element) {
    if (!element) {
        console.error('Invalid element provided');
        return;
    }

    // Create a new touch event
    var touch = new Touch({
        identifier: Date.now(),
        target: element,
        clientX: 0,
        clientY: 0,
        pageX: 0,
        pageY: 0,
        screenX: 0,
        screenY: 0,
    });

    var touchEvent = new TouchEvent('touchstart', {
        bubbles: true,
        cancelable: true,
        composed: true,
        touches: [touch],
        targetTouches: [touch],
        changedTouches: [touch],
    });

    // Dispatch the touch event on the element
    element.dispatchEvent(touchEvent);
}




function getOffsetTop(element) {
    var offsetTop = 0;
    while (element) {
        offsetTop += element.offsetTop;
        element = element.offsetParent;
    }
    return offsetTop;
}




// Nadaj klase na scoll to do animacji elementów

function odslonElementy() {
    var odslaniane = document.querySelectorAll(".animowane");

    for (var i = 0; i < odslaniane.length; i++) {
        var windowHeight = window.innerHeight;
        var elementTop = odslaniane[i].getBoundingClientRect().top;
        var elementVisible = 150;

        if (elementTop < windowHeight - elementVisible) {
            odslaniane[i].classList.add("anim-ctive");
        } else {
            odslaniane[i].classList.remove("anim-active");
        }
    }
}

window.addEventListener("scroll", odslonElementy);




// Funkcja obsługująca animowany podjazd do kotwicy
function animowanyPodjazDoKotwicy() {
    // Znajdź wszystkie linki w nawigacji
    const nawigacjaLinki = document.querySelectorAll('nav a.wp-block-navigation-item__content');

    // Dla każdego znalezionego linka
    nawigacjaLinki.forEach(function (link) {
        // Dodaj nasłuchiwanie na zdarzenie kliknięcia
        link.addEventListener('click', function (e) {
            e.preventDefault();

            // Pobierz identyfikator elementu docelowego z atrybutu href
            const celId = this.getAttribute('href').substring(1);
            // Znajdź element docelowy po jego identyfikatorze
            const celElement = document.getElementById(celId);
            
            console.log(celElement);

            console.log(getOffsetTop(celElement));
            
            // Jeśli element docelowy istnieje
            if (celElement) {
                // Animuj przewijanie do elementu docelowego
                gsap.to(window, {
                    duration: 0.5,
                    scrollTo: {
                        y: getOffsetTop(celElement) - 140
                    }
                });
            }
        });

        // Dodaj obsługę zdarzenia dotknięcia (touch)
        link.addEventListener('touchstart', function (e) {
            // Zamknij menu mobilne, jeśli jest otwarte
            var menuMobilne = document.querySelector('.wp-block-navigation__responsive-container.is-menu-open');
            menuMobilne.classList.remove('is-menu-open');
            menuMobilne.classList.remove('has-modal-open');

            e.preventDefault();

            // Pobierz identyfikator elementu docelowego z atrybutu href
            const celId = this.getAttribute('href').substring(1);
            // Znajdź element docelowy po jego identyfikatorze
            const celElement = document.getElementById(celId);

            // Pobierz element odpowiedzialny za zamknięcie menu mobilnego
            var wyjscie = document.querySelector('.wp-block-navigation__responsive-container-close');
            // Wywołaj funkcję symulującą zdarzenie dotknięcia
            triggerTouchEvent(wyjscie);

            // Jeśli element docelowy istnieje
            if (celElement) {
                // Animuj przewijanie do elementu docelowego
                gsap.to(window, {
                    duration: 0.5,
                    scrollTo: {
                        y: getOffsetTop(celElement) -140
                    }
                });
            }
        });
    });
}

// Wywołaj funkcję obsługującą animowany podjazd do kotwicy
animowanyPodjazDoKotwicy();

Update

Tworzenie animowanego scrolla do kotwicy na stronach WordPress może znacznie poprawić doświadczenie użytkowników, zwłaszcza na urządzeniach mobilnych. Poniżej przedstawiamy, jak skonfigurować tę funkcję, używając bibliotek GSAP i ScrollToPlugin.

Wprowadzenie

Aby zrealizować animowany scroll do kotwicy, należy włączyć odpowiednie skrypty w pliku functions.php:

functions.php

    wp_enqueue_script('gsap', 'https://cdnjs.cloudflare.com/ajax/libs/gsap/3.12.2/gsap.min.js', array(), '1.0', true);
    wp_enqueue_script('scrolltoplugin', 'https://cdnjs.cloudflare.com/ajax/libs/gsap/3.12.2/ScrollToPlugin.min.js', array(), '1.0', true);

Skrypt JavaScript

Następnie, użyjemy poniższego skryptu, aby dodać funkcjonalność animowanego przewijania:



// Funkcja obsługująca animowany podjazd do kotwicy
function animowanyPodjazDoKotwicy() {
  // Znajdź wszystkie linki w nawigacji
  const nawigacjaLinki = document.querySelectorAll('nav a.wp-block-navigation-item__content');

  // Dla każdego znalezionego linka
  nawigacjaLinki.forEach(function (link) {
    // Dodaj nasłuchiwanie na zdarzenie kliknięcia
    link.addEventListener('click', function (e) {
      e.preventDefault();

      // Pobierz identyfikator elementu docelowego z atrybutu href
      const celId = this.getAttribute('href').substring(1);
      // Znajdź element docelowy po jego identyfikatorze
      const celElement = document.getElementById(celId);

      // Jeśli element docelowy istnieje
      if (celElement) {
        // Animuj przewijanie do elementu docelowego
        gsap.to(window, { duration: 0.5, scrollTo: { y: celElement.offsetTop - 140 } });
      }
    });

    // Dodaj obsługę zdarzenia dotknięcia (touch)
    link.addEventListener('touchstart', function (e) {
      // Zamknij menu mobilne, jeśli jest otwarte
      var menuMobilne = document.querySelector('.wp-block-navigation__responsive-container.is-menu-open');
      menuMobilne.classList.remove('is-menu-open');
      menuMobilne.classList.remove('has-modal-open');

      e.preventDefault();

      // Pobierz identyfikator elementu docelowego z atrybutu href
      const celId = this.getAttribute('href').substring(1);
      // Znajdź element docelowy po jego identyfikatorze
      const celElement = document.getElementById(celId);

      // Pobierz element odpowiedzialny za zamknięcie menu mobilnego
      var wyjscie = document.querySelector('.wp-block-navigation__responsive-container-close');
      // Wywołaj funkcję symulującą zdarzenie dotknięcia
      //triggerTouchEvent(wyjscie);

      // Jeśli element docelowy istnieje
      if (celElement) {
        // Animuj przewijanie do elementu docelowego
        gsap.to(window, { duration: 0.5, scrollTo: { y: celElement.offsetTop - 140 } });
      }
    });
  });
}

// Wywołaj funkcję obsługującą animowany podjazd do kotwicy
animowanyPodjazDoKotwicy();

Dzięki tym krokom, Twoje strony będą wyglądać bardziej profesjonalnie i będą bardziej przyjazne użytkownikom mobilnym.


Prosta wersja bez bibliotek nie zawsze działa na mobile

function animowanyPodjazDoKotwicy(){
const nawigacjaLinki = document.querySelectorAll(‘nav a’);

nawigacjaLinki.forEach(function (link) {
link.addEventListener(‘click’, function (e) {
e.preventDefault();

const celId = this.getAttribute(‘href’).substring(1);
const celElement = document.getElementById(celId);

if (celElement) {
plynniePrzewinDo(celElement);
}
});
});

function plynniePrzewinDo(celElement) {
const pozycjaPoczatkowa = window.pageYOffset;
const pozycjaDocelowa = celElement.getBoundingClientRect().top + pozycjaPoczatkowa;
const czasTrwania = 1000; // Czas trwania animacji w milisekundach
const czasRozpoczecia = performance.now();

function animuj(aktualnyCzas) {
const uplyneloCzasu = aktualnyCzas – czasRozpoczecia;
const postep = Math.min(uplyneloCzasu / czasTrwania, 1);

window.scrollTo(0, pozycjaPoczatkowa + (pozycjaDocelowa – pozycjaPoczatkowa) * postep);

if (postep < 1) {
requestAnimationFrame(animuj);
}
}

requestAnimationFrame(animuj);
}
}
animowanyPodjazDoKotwicy();