ventana tutorial propiedades open metodos instrucciones hija flotante emergente basico javascript html5 reflow

tutorial - ventana hija javascript



¿Hay una manera de detectar el desplazamiento horizontal solo sin desencadenar un reflujo del navegador? (7)

¿Qué hay de escuchar la entrada directamente?

element.addEventListener(''wheel'', e => { if ( e.deltaX !== 0 ) { horizontal(); } if ( e.deltaY !== 0 ) { vertical(); } })

También es posible que necesites crear tus propias barras de desplazamiento y escuchar cómo arrastrarlas. Está reinventando la rueda (jajaja), pero bueno, no hay scrollTop o scrollLeft a la vista.

Puede detectar un evento de desplazamiento del navegador en un elemento arbitrario con:

element.addEventListener(''scroll'', function (event) { // do something });

Me gustaría poder diferenciar entre desplazamiento vertical y desplazamiento horizontal y ejecutar acciones para ellos de forma independiente.

Actualmente estoy haciendo esto escondiendo los valores de element.scrollTop y element.scrollLeft, y luego comparándolos dentro del detector de eventos. P.ej

var scrollLeft, scrollTop; element.addEventListener(''scroll'', function (event) { if (scrollLeft !== element.scrollLeft) { // horizontally scrolled scrollLeft = element.scrollLeft; } if (scrollTop !== element.scrollTop) { // vertically scrolled scrollTop = element.scrollTop; } });

Esto funciona bien, sin embargo, desde https://gist.github.com/paulirish/5d52fb081b3570c81e3a leí que leer los valores de scrollLeft o scrollTop provoca un reflujo.

¿Hay una mejor manera de hacer esto sin causar un reflujo del navegador en el desplazamiento?


Como se dijo en la respuesta de @Nelson, no hay forma de verificar entre desplazamiento horizontal y vertical, y la razón es que el objeto de evento activado tiene cero información sobre él (lo acabo de verificar).

Mozilla tiene un montón de ejemplos de cómo controlar la comprobación de propiedades del elemento, pero personalmente prefiero el enfoque setTimeout , porque puede ajustar la respuesta del FPS para que se ajuste a sus necesidades. Con eso en mente, escribí este ejemplo de lectura a uso:

<html> <head> <meta charset="utf-8"/> <style> #foo { display: inline-block; width: 500px; height: 500px; overflow: auto; } #baz { display: inline-block; background: yellow; width: 1000px; height: 1000px; } </style> </head> <body> <div id="foo"> <div id="baz"></div> </div> <script> // Using ES5 syntax, with ES6 classes would be easier. function WaitedScroll(elem, framesPerSecond, onHorz, onVert) { this.isWaiting = false; this.prevLeft = 0; this.prevTop = 0; var _this = this; elem.addEventListener(''scroll'', function() { if (!_this.isWaiting) { _this.isWaiting = true; setTimeout(function() { _this.isWaiting = false; var curLeft = elem.scrollLeft; if (_this.prevLeft !== curLeft) { _this.prevLeft = curLeft; if (onHorz) onHorz(); } var curTop = elem.scrollTop; if (_this.prevTop !== curTop) { _this.prevTop = curTop; if (onVert) onVert(); } }, 1000 / framesPerSecond); } }); } // Usage with your callbacks: var waiter = new WaitedScroll( document.getElementById(''foo''), // target object to watch 15, // frames per second response function() { // horizontal scroll callback console.log(''horz''); }, function() { // vertical scroll callback console.log(''veeeeeeeertical''); } ); </script> </body> </html>


Creo que su código es correcto, porque al final del día necesita leer una de esas propiedades para averiguar la dirección de desplazamiento, pero la clave aquí para evitar problemas de rendimiento es acelerar el evento , porque de lo contrario se scroll evento de scroll con demasiada frecuencia y esa es la causa raíz de los problemas de rendimiento.

Entonces, su código de ejemplo adaptado para estrangular el evento de scroll sería así:

var ticking = false; var lastScrollLeft = 0; $(window).scroll(function() { if (!ticking) { window.requestAnimationFrame(function() { var documentScrollLeft = $(document).scrollLeft(); if (lastScrollLeft != documentScrollLeft) { console.log(''scroll x''); lastScrollLeft = documentScrollLeft; } ticking = false; }); ticking = true; } });

Fuente: https://developer.mozilla.org/en-US/docs/Web/Events/scroll#Example


Elementos que utilizan la position: absolute; Se sacan del flujo de documentos (ver fuente) .

Con esto en mente, puedes usar CSS para hacer que tu element esté absolutamente posicionado dentro de su elemento primario ...

#parent{ width: 500px; height: 100px; // ...or whatever dimensions you need the scroll area to be position: relative; } #element{ position: absolute; top: 0px; left: 0px; bottom: 0px; right: 0px; }

... y luego puede sentirse libre de leer los element.scrollLeft y element.scrollTop como lo hizo en su pregunta original sin temor a que los cuellos de botella vuelvan a afectar a todo el DOM.

Este enfoque también se recomienda en las directrices para desarrolladores de Google .


Espero que en realidad no ...

Pero de acuerdo a ¿Cómo detectar el desplazamiento horizontal en jQuery? puede intentar:

var lastScrollLeft = 0; $(window).scroll(function() { var documentScrollLeft = $(document).scrollLeft(); if (lastScrollLeft != documentScrollLeft) { console.log(''scroll x''); lastScrollLeft = documentScrollLeft; } });

Necesidad de cronometrarlo para volver a verificar qué método es el más rápido ...


Prueba fast-dom biblioteca de fast-dom :

Ejecute el código de ejemplo en su lado localmente para obtener los datos de perfiles correctos.

import fastdom from ''fastdom'' let scrollLeft let scrollTop const fast = document.getElementById(`fast-dom`) fast.addEventListener(`scroll`, function fastDom() { fastdom.measure(() => { if (scrollLeft !== fast.scrollLeft) { scrollLeft = fast.scrollLeft console.log(scrollLeft) } if (scrollTop !== fast.scrollTop) { scrollTop = fast.scrollTop console.log(scrollTop) } }) })