Как проверить, что элемент/блок/тег помещается на экран (Отслеживание прокрутки страницы).

27.01.2019 06:51:46

Задача: производить набор действий, если посетитель сайта промотал (проскролил) страницу до нужного элемента.

Например, подсвечивать пункт меню на лендинг странице. Иногда такое называют spyscroll.

Самый напрашивающийся способ - просто проверять насколько пикселей пользователь проскролил страницу, но нужно учитывать, что у людей может быть разное разрешение (да и вообще разное устройство) и высота экрана может быть разной. Кроме этого, если верстка адаптивная, то блоки на страницы могут располагаться совершенно в разном порядке.

Способ решения: даем всем нужным элементам определенный класс, вешаем на событие onresize поиск всех нужных элементов и записываем координаты их отступа от верхней границы документа, а на событии onscroll, проверяем что человек доскролил до нужных координат.

Отдельно отмечу, что для определения верхней границы стоит использовать getBoundingClientRect вместо offsetTop, т.к. последний возвращает координаты не относительно родительского блока, а не всего документа.

Сам код, немного излишний, но зато демонстрирует отправку данных в google dataLayer

 
$(function() {

    var scene = {
        send: function(data, action, interaction){
            window.dataLayer.push({
                'ecommerce': data,
                'event': 'gtm-ee-event',
                'gtm-ee-event-category': 'Enhanced Ecommerce',
                'gtm-ee-event-action': action,
                'gtm-ee-event-non-interaction': interaction
            });
        },

 
        bindControlls : function()
        {
            var oThis = this;
 
            this.el.items.on( "click", function (event){
                var info = $(this).data('tinfo');
                    action = $(this).data('tname1')
                ;
                oThis.send.call(oThis, info, action, 'False');
            });

            $( window ).resize(function() {
                oThis.doResize();
            });

            $( window ).scroll (function() {
                oThis.doScroll();
            });
        },


        cacheElements : function()
        {
            this.el.items = $(".sogtmdl_click");
        },

        doScroll: function (){
            var items_top = this.vars.items_top,
                items = this.el.items,
                scrollPosition = document.documentElement.scrollTop || document.body.scrollTop
            ;
            
            scrollPosition = scrollPosition + window.innerHeight;
            
// console.debug(scrollPosition); // scroll
            for(var i = 0; i < items_top.length; i++){
                if(!items_top[i].sended)
                {
                    if (items_top[i].top <= scrollPosition) {
                        var oItem = items[i],
                            info = $(oItem).data('tinfo');
                            action = $(oItem).data('tname2')
                        ;
                        this.vars.items_top[i].sended = true;
                        
                        this.send(info, action, 'True');
//                        console.debug(info);
                    }
                }
            }
        },

        doResize: function (){
            var items = this.el.items;
            this.vars.items_top = [];

            for(var i = 0; i < items.length; i++){
                
                
                this.vars.items_top.push({
                    id: i, 
                    //top: items[i].offsetTop,
                    top: items[i].getBoundingClientRect().top,
                    sended: false
                });
// console.debug(items[i].offsetTop); scroll
            }
            
/*
            for(var i = 0; i < items_top.length; i++){
                console.debug(this.vars.items_top[i].id + " - " + this.vars.items_top[i].top);
            }
*/
        },

        init: function (){
            this.cacheElements();
            this.bindControlls();
            this.doResize();
            this.doScroll();
        }
    }
    scene.init();


});

Есть системные пометки.

Категории: JQuery
Яндекс.Метрика