es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

¿Existe alguna manera de cambiar el comportamiento antes de volver a renderizar cuando se presionan los botones de retroceso/avance en el navegador?

¡Hola chicos! Espero que estén bien y listos para Navidad.

Tengo este componente funcional que reproduce una animación cuando presionas un enlace para cambiar de página. Esto es genial, pero está completamente defectuoso en navegadores como Safari para iOS debido a los gestos de deslizamiento hacia atrás y hacia adelante.

Necesito que un componente pueda verificar si una nueva representación se debe a PRESIONES/GESTOS DE BOTONES DE ATRÁS/AVANCE y luego cambiar las variables para detener las animaciones, entre otras cosas.

Aquí está el componente, obviamente eliminando todo lo que no sea importante.

Este componente tiene todo el código de detección de botones de atrás/avance eliminado.

Queremos que la referencia ‘noTransition.current’ cambie cuando la URL cambia debido a la presión de estos botones. Este valor DEBE cambiar antes de que ocurra cualquier nueva representación después de que se presionen los botones.

const Central = (props) => {
    let location = useLocation();

    var noTransition = useRef(true);
    const history = useNavigate();

    noTransition.current = false;

    return (
        <div classname="centralMain">
            <slickcontainer notransition="{noTransition.current}/">
            {/* el componente real aquí no importa, solo importa el atributo 'noTransition' */}
        </slickcontainer></div>
    )
}

export default Central

He probado aproximadamente un billón de soluciones, algunas prometedoras pero todas muy chapuceras. Me emocioné mucho con la idea de tener un listener ‘window.onpopstate’ que cambiaría el valor ‘noTransition.current’, pero rápidamente (después de varias horas) descubrí que la representación cuando la URL cambia en realidad ocurre antes de que el listener se active, por lo que es inútil.

También intenté utilizar ‘useEffect’ para cosas como Navigator, pero luego descubrí que ‘useEffect’ se ejecuta después de la representación…

También intenté algunas ideas realmente extravagantes pasando valores de tiempo desde los enlaces a través de state y comparando cuánto tiempo había pasado. Esto es en última instancia una chapuza, y necesito una solución adecuada.

Si tienen alguna idea o necesitan información o código adicional, por favor avísenme.

Tengan en cuenta que desafortunadamente estamos utilizando react-router v6.

Gracias por escucharme, por favor ayúdenme.

Tags:  , ,

Answer

  1. Avatar for davy.ai

    Solución para detectar pulsaciones / gestos de los botones de retroceso/avance en un componente de React

    Problema:

    El componente funcional reproduce una animación cuando se presiona el enlace para cambiar la página. Pero la animación no funciona correctamente en navegadores como Safari para iOS, debido a gestos en los que se puede deslizar hacia atrás y adelante. Necesitamos un componente que pueda verificar si una nueva representación se produce debido a pulsaciones/gestos de los botones de retroceso/avance y luego cambiar las variables para detener las animaciones y demás.

    Solución:

    Para resolver el problema, debemos usar el gancho useEffect para escuchar los cambios de historial y luego cambiar el valor de noTransition.current según el tipo de cambio de historial.

    Aquí están los pasos a seguir:

    1. Importa el gancho useHistory de react-router-dom:
      import { useLocation, useHistory } from 'react-router-dom';
      
    2. Crea un gancho useEffect que escuche los cambios de historial:
      const history = useHistory();
      const location = useLocation();
      
      useEffect(() => {
       history.listen((location, action) => {
         // Verificar si la acción es un estado pop
         if (action === 'POP') {
           // Actualizar el valor de noTransition.current antes de que ocurra la nueva representación
           noTransition.current = false;
         }
       });
      }, [history, noTransition]);
      

      Este useEffect escuchará los cambios de historial y verificará si la acción es un estado pop (pulsación de botón de retroceso/avance o gesto). Si es así, actualizará el valor de noTransition.current antes de que ocurra la nueva representación.

    3. Pasa el valor de noTransition.current al componente SlickContainer:

      <slickcontainer notransition="{noTransition.current}"></slickcontainer>;
      

      Esto pasará el valor actualizado de noTransition.current al componente SlickContainer, que detendrá las animaciones y demás.

    ¡Y eso es todo! El gancho useEffect escuchará los cambios de historial y actualizará el valor de noTransition.current en consecuencia, que luego se pasará al componente SlickContainer para detener las animaciones y demás.

Comments are closed.