
Traducción de "
RTL Styling 101 - Una extensa guía sobre cómo diseñar RTL en CSS " por Ahmad Shadid.
Más de 292 millones de personas en todo el mundo hablan árabe como lengua materna. Les pertenezco, por lo que a veces desarrollo sitios que deberían admitir ambas direcciones de escritura de texto: de izquierda a derecha (LTR - De izquierda a derecha) y de derecha a izquierda (de derecha a izquierda).
Introducción al estilo RTL
CSS usa la dirección LTR por defecto. Si marca los estilos del navegador para el elemento html, verá que para la propiedad dir (o "dirección"), el valor ltr es el valor predeterminado. El siguiente es un ejemplo básico para demostrar la diferencia entre el marcado LTR y RTL.

Presta atención al bloque RTL: a diferencia de LTR, el texto se lee de derecha a izquierda. En este sencillo ejemplo, el navegador lo mostró correctamente. Para cambiar la dirección del idioma del documento, debe agregar el atributo dir al elemento raíz.
<html dir="rtl">...</html>
Cuando el valor dir cambia, todos los elementos anidados deberían cambiar automáticamente a continuación: encabezados, párrafos, enlaces, imágenes y formularios.
También vale la pena mencionar que el atributo dir se puede establecer en "auto", lo que cambiará automáticamente la dirección del elemento en función de un análisis de su contenido. De acuerdo con la especificación HTML:
Los autores instan a que este valor se use solo como último recurso, cuando la dirección del texto es realmente desconocida y no hay forma de determinarlo de manera efectiva en el lado del servidor.
Además de establecer el atributo dir = rtl para el elemento HTML, también podemos agregar direction: rtl como un estilo CSS.
.element { direction: rtl; }
Sin embargo, CSSWG (el grupo de trabajo de CSS) recomienda definir la dirección exactamente como un atributo para el elemento raíz HTML para garantizar que el marcado sea correcto, independientemente de si CSS está presente o no.
Ejemplo de cambio de dirección del marcado
Veamos un ejemplo más detallado para comprender mejor cómo cambiar la dirección de marcado de LTR a RTL.

<article class="media"> <img class="media__photo" src="blueberry-cheesecake.jpg" alt=""> <div class="media__content"> <h2>Blueberry Cheesecake</h2> <p>...</p> <p><a href="#" class="link">View Recipe</a></p> </div> </article>
Inicialmente, utilicé el viejo flotador para justificar a la izquierda la imagen en el marcado LTR y, por supuesto, apliqué clearfix.
.media:after { content: ""; display: block; clear: both; } .media img { float: left; width: 200px; margin-right: 16px; }
Luego agregamos dir = “rtl” para el elemento que contiene texto en árabe. Se obtiene el siguiente resultado:

Todos los elementos están alineados en el lado derecho, excepto la imagen. Esto sucedió porque la propiedad de la imagen estaba configurada como flotante: izquierda y margen derecha: 16px. Para solucionar esto, anule los siguientes estilos
.media[dir="rtl"] img { float: right; margin-right: 0; margin-left: 16px; }
Contenido en inglés y árabe en diseño LTR
¿Qué sucede si algún texto tiene una mezcla de palabras en inglés y árabe, y el marcado está en la dirección de LTR? El resultado es extraño.

El navegador no mostrará el título correctamente. Los hablantes de árabe serán confusos. Las palabras en este encabezado deben estar en el orden que se muestra en la imagen a continuación. Solo comenzando por la derecha.

Para evitar este problema, establezca la dirección de idioma apropiada siempre que sea posible. Si el elemento se establece en el atributo dir = "rtl", se mostrará como se esperaba.

La situación puede volverse aún más complicada si el título es largo. A continuación lo completé un poco y el resultado fue inesperado. Indiqué con números la secuencia correcta. De nuevo, comenzando desde la derecha.

Cuando se establece el atributo dir = “rtl” para el elemento, el título se vuelve correcto. Es decir, la oración se ve gramaticalmente correcta y las palabras están ordenadas en la secuencia correcta.

Flexbox
Flexbox básicamente tiene en cuenta el modo de escritura establecido en el documento. Este factor se utiliza para determinar cómo se alinearán los bloques en la página de forma predeterminada. Por ejemplo, en un sitio en inglés irán de izquierda a derecha y en chino de arriba a abajo. Para inglés y árabe, la propiedad predeterminada del modo de escritura es horizontal-tb.
Según la
red de desarrolladores de Mozilla (MDN), un valor de tb horizontal significa lo siguiente:
El contenido se coloca horizontalmente de izquierda a derecha, verticalmente de arriba a abajo. La siguiente línea horizontal está debajo de la anterior.
Cuando la dirección de la página cambia a RTL, flexbox expande adecuadamente el flujo de sus elementos. Esta es una gran ventaja! La siguiente imagen muestra cómo gira el eje flexbox, según el valor de la propiedad de dirección.

En el siguiente ejemplo, creé tres elementos y los numeré para mostrar la diferencia al cambiar la dirección de la página.
<div class="element"> <div class="item"^_^gt lt^_^/div> <div class="item"^_^gt lt^_^/div> <div class="item"^_^gt lt^_^/div> </div>
.element { display: flex; flex-direction: row; }

Rejilla CSS
Al igual que flexbox, la cuadrícula css depende del modo de escritura del documento, lo que nos brinda las mismas ventajas que cuando se usa flexbox.
En el siguiente ejemplo, para la dirección LTR, la barra lateral debe estar a la izquierda y principal a la derecha. Para RTL, lo contrario es cierto. Cuando usamos CSS Grid, esta reconstrucción se realizará automáticamente de acuerdo con la dirección establecida en esta página.
<div class="element"> <div class="side">Side</div> <div class="main">Main</div> </div>
.element { display: grid; grid-template-columns: 220px 1fr; grid-gap: 1rem; }
Errores principales al cambiar a la dirección RTL
Los desarrolladores no árabes cometen errores comunes que son inmediatamente evidentes para los hablantes nativos.
1. Espacio entre letras
En inglés, es común usar la propiedad de espacio entre letras para controlar el espacio entre letras dentro de una palabra. Considere el siguiente ejemplo con contenido en inglés. Se ve bastante normal.

Sin embargo, si agrega el mismo espacio entre letras al texto árabe, se verá muy extraño. Considere el siguiente ejemplo de la vida real.

Tenga en cuenta que en el texto al que se aplica la propiedad de espacio entre letras, las letras de cada palabra se separan entre sí. Esto esta mal. Las letras árabes deben verse conectadas, y mantener el mismo espacio entre letras que en inglés evita esto. Asegúrese de que cuando trabaje con un sitio multilingüe, no olvide establecer la propiedad de espacio entre letras: 0 en el lugar correcto.
2. Transparencia de texto
En el diseño de sitios web, el texto a menudo se hace translúcido. Por ejemplo, para marcar su importancia secundaria. Esto funciona para inglés. Sin embargo, si el contenido está en árabe, puede surgir un problema debido a la extraña forma de representar el texto.

Aparecen lugares en los que el color del contorno del personaje cambia debido a su superposición. En este ejemplo, la propiedad de espacio entre letras no se estableció, por lo que no afecta el problema. La solución es establecer colores sin translucidez (que generalmente se establece a través de RGBa u opacidad).
3. Diferencias en el tamaño de las palabras en diferentes idiomas.
A veces, cuando un sitio se traduce al árabe, el tamaño de los elementos cambia debido al hecho de que algunas palabras después de la traducción se hacen más grandes o más pequeñas. Considere el siguiente ejemplo, en el que simulé la navegación del sitio de Smashing Magazine.

En la versión árabe, algunas de las palabras son casi del mismo tamaño que sus versiones en inglés, algunas son exactamente iguales y otras son más grandes. Para hacerlo más claro, aquí hay una comparación de cada palabra y su traducción al árabe.

Quizás se pregunte por qué estoy hablando de la diferencia en el tamaño de las palabras en diferentes idiomas, ya que esto es normal y esperado. Considere el siguiente ejemplo de LinkedIn del mundo real.

El botón "Listo" se traduce al árabe como "تم", por lo que se vuelve bastante pequeño y generalmente se ve extraño. Especialmente para tales casos, sería mejor establecer la propiedad de ancho mínimo para el botón. Lo agregué a través del panel de desarrolladores para mostrar cómo debería verse:

Aquí hay un ejemplo muy similar de Twitter:

Tenga en cuenta que los problemas anteriores con LinkedIn y Twitter se descubrieron al momento de escribir (13 de diciembre de 2019).
4. Truncamiento de texto
Una vez trabajé en un proyecto multilingüe y me encontré con un problema relacionado con truncar texto en la dirección incorrecta. Considere el siguiente ejemplo.

El truncamiento para el texto en inglés es incorrecto. Esto debería suceder al final del elemento, no al principio. Para resolver este problema, debe establecer el atributo dir = "auto" para este elemento, y luego el navegador analizará automáticamente el contenido y decidirá qué valor dir aplicará.
<p dir="auto">أهلاً وسهلاً بكم في المقال الذي يتحدث عن تصميم صفحات الويب للغة العربية</p> <p dir="auto">Welcome to the article that explains how to design for RTL pages.</p>

5. Elegir una fuente RTL incorrecta
La presencia de una versión RTL del sitio no significa que simplemente pueda limitarse a especificar la fuente del sistema instalada por el usuario de manera predeterminada. Debe tomar esto en serio para garantizar una buena legibilidad. Un ejemplo de selección de una fuente fallida es Twitter:

Desde el punto de vista de habla árabe, la palabra "تغريد" es difícil de leer por varias razones:
- fuente no muy buena
- la gordura perjudica la legibilidad
- los puntos de la palabra son muy pequeños y muy cercanos a las letras
Di algunos ejemplos que parecen mucho más claros:

6. Mezclando números hindi y arábigos
En árabe, hay dos formas de escribir números:
- Hindi: ١ ٢ ٣ ٤ ٥ ٦ ٧ ٨ ٩
- Árabe: 0 1 2 3 4 5 6 7 8 9
Los números utilizados en inglés se heredan del árabe: "0, 1, 2, 3, 4, 5, 6, 7, 8, 9". El texto que contiene números debe coincidir solo con una de las dos opciones: hindi o árabe.
De acuerdo con Wikipedia:
La razón por la que en Europa y América los números se llaman "árabe" es porque fueron introducidos en Europa en el siglo X por personas de habla árabe del norte de África.
El siguiente ejemplo contiene una mezcla de números hindi y arábigos. Este enfoque parece inconsistente y se debe usar un solo estilo en su lugar.

Momentos que pueden no funcionar con RTL
1. Altura de línea (altura de línea)
Por lo general, se establece una fuente separada para el marcado RTL. En este caso, verifique cómo se ve el contenido en una o más líneas. En el siguiente ejemplo, hay menos espacio entre las líneas para el texto árabe que para el inglés, aunque tengan el mismo valor para la propiedad de altura de línea.

Es importante tener esto en cuenta y establecer el valor correcto para la altura de línea para el texto árabe.
Twitter, por ejemplo, tiene un botón con contenido recortado. Solo por el valor incorrecto de altura de línea.

Tenga en cuenta que en la primera imagen, el diacrítico árabe se recorta. Se llama kasra y es muy importante para la lectura correcta de la palabra. En la siguiente imagen, corregí la altura de la línea y ahora los caracteres se muestran completamente, sin recortar.
2. Enlaces subrayados
Con palabras en árabe, el subrayado estándar de los enlaces de CSS se ve mal. Esto se debe a las peculiaridades de escribir palabras y letras en árabe y se muestra en la siguiente imagen:

Marqué las áreas problemáticas con un círculo rojo. El subrayado se superpone a los puntos de las letras. Aquí hay un primer plano:

Los puntos marcados con un círculo rojo se superponen con un subrayado, lo que dificulta la lectura. La solución es personalizar el subrayado con CSS.
2.1. Tipografía (decoración de texto)
Es posible cambiar el estilo y el color del subrayado utilizando las nuevas propiedades text-decoration-style y text-decoration-color. Sin embargo, no hay garantía de que esto funcione correctamente con todas las familias y tamaños de fuente. Al momento de escribir, Firefox es el navegador con el mejor soporte para estas funciones.
.link-2 { text-decoration-color: rgba(21, 132, 196, 0.2); text-decoration-style: normal; text-underline-offset: 4px; text-decoration-thickness: 2px; }

2.2 Sombra (cuadro-sombra)
El soporte del navegador para la propiedad box-shadow es mucho mejor que la decoración de texto. Puede verificar el soporte para una de las nuevas propiedades de decoración de texto, y si el navegador no lo admite, aplique un respaldo utilizando la propiedad de sombra de cuadro.
.link-3 { color: #000; text-decoration-color: rgba(21, 132, 196, 0.2); text-decoration-style: normal; text-underline-offset: 4px; text-decoration-thickness: 2px; box-shadow: inset 0 -5px 0 0 rgba(#1584c4, 0.2); } @supports (text-decoration-color: red){ .link-3 { box-shadow: none; } }

3. Salto de línea
Si utiliza la propiedad de salto de palabra, debe verificar la corrección de su funcionamiento. Eche un vistazo al siguiente ejemplo:

Las áreas encerradas en un círculo son palabras árabes divididas por saltos de línea debido al uso del salto de palabras. Y en árabe, no se usa el ajuste de palabras, porque las letras de cada palabra deben estar conectadas entre sí.
4. Abreviaturas
En inglés, las abreviaturas se usan a menudo, por ejemplo, para días de la semana. Por lo tanto, "Sábado" se convierte en "Sábado".

En árabe, esto no es posible en principio, ya que las letras de la palabra deben estar conectadas.

Iconos bidireccionales
No es necesario voltear los iconos simétricos cuando se cambia entre diseños LTR y RTL. Aquí hay algunos ejemplos:

Al mismo tiempo, para algunos iconos es importante cambiar la dirección en la versión RTL del sitio para que el usuario los entienda correctamente.

Voltear artículos
Mientras trabajo en algunos componentes, necesito una forma de voltearlos rápidamente. En Sketch, copio el componente y lo volteo con el comando apropiado. La misma funcionalidad está disponible en Adobe XD y Figma.

Para ver a qué me refiero, aquí hay una animación que demuestra lo que hago después de voltear el componente.

Características de diseño para RTL
En esta sección, examinaré los componentes más comunes y mostraré cómo deberían verse en modo RTL.
Iconos de botones
Hay situaciones en las que el botón tiene un icono que abre un menú de acciones adicionales. En este caso, la ubicación del icono debe invertirse en el diseño RTL.

Campos de entrada
Algunos campos de entrada de formulario deben permanecer alineados a la izquierda incluso en modo RTL. Por ejemplo, ingrese campos de correo electrónico o números de teléfono.

Migas de pan
Las flechas entre las secciones en migas de pan también deben rotarse.

Título de la página
El componente de encabezado de página contiene las secciones de inicio y fin. Ambos deben girarse en RTL

Mesas
Las tablas también deben girarse.

Marcadores
Si el icono está a la izquierda del nombre en los marcadores en modo LTR, este componente debe expandirse en RTL.

Tarjeta
Para una tarjeta horizontal, la imagen y el texto deben intercambiarse en RTL

Notificaciones emergentes
Como es de esperar, los iconos de "cerrar" y "advertencia" deben intercambiarse

Propiedades booleanas de CSS
De acuerdo con MDN:
Propiedades y valores lógicos CSS es un módulo que representa propiedades y valores lógicos que proporcionan la capacidad de controlar el diseño utilizando direcciones y dimensiones lógicas en lugar de físicas.
Tomemos un ejemplo simple. Supongamos que necesitamos alinear una línea de texto a la derecha. Agregue lo siguiente:
.page-header { text-align: right; }
Y para RTL:
[dir="rtl"] .nav-item { text-align: left; }
¿Qué pasaría si hubiera una manera de agregar solo un valor para la propiedad de alineación de texto, que cambiaría el lado de alineación, dada la dirección de la página? ¡Las propiedades lógicas de CSS vienen al rescate!
.page-header { text-align: end; }
Al usarlo, el lado especificado por la propiedad de alineación de texto se basará en la dirección de la página.
DemoPara que sea más fácil ver la diferencia entre el inicio y el final, preparé el diagrama a continuación. El valor inicial es equivalente al valor izquierdo en LRT y al valor derecho en RTL. Lo mismo con el final, todo lo contrario.

Ahora que tiene una idea general de cómo funciona esto, veamos ejemplos adicionales y formas de aplicar las propiedades lógicas de CSS.
Acolchado lógico

Supongamos que tenemos un campo de entrada con un icono de búsqueda a la derecha. Tenemos que establecer el relleno en ambos lados. El relleno de la derecha será un poco más grande para evitar superponer el ícono en el texto.
.input--search { padding-inline-start: 1rem; padding-inline-end: 2.5rem; }
Margen lógico

El margen a la derecha del ícono debe ser lógico, por lo que usamos margin-inline-end para esto.
.page-header__avatar { margin-inline-end: 1rem; }
Marcos lógicos (borde)

A menudo se usa un marco para indicar un elemento de navegación activo. En el ejemplo anterior, se establece un marco en el lado izquierdo de cada elemento. ¿Cómo implementar esto usando propiedades lógicas?
.nav__item { border-inline-start: 3px solid transparent; } .nav__item.is-active { border-color: #1e9ada; }
Redondeo lógico de esquinas (radio de borde)

En la imagen de arriba, el fondo del elemento de navegación se redondea solo para las esquinas superior derecha e izquierda. Esto se puede implementar usando propiedades lógicas:
.nav__item { border-start-end-radius: 30px; border-end-end-radius: 30px; background-color: transparent; } .nav__item.is-active { background-color: #ecf6fb; }
Propiedades lógicas de la hoja de trucos
Si tiene dudas sobre la elección de un análogo lógico de la propiedad que define el lado, puede echar un vistazo a la hoja de trucos a continuación. Tenga en cuenta que contiene solo las propiedades lógicas que pueden ser útiles al trabajar con los modos LTR y RTL. Compilé esta hoja de trucos basada en un maravilloso
artículo de Adrian Roselli.
https://codepen.io/shadeed/pen/2981e62691e67452d9f282a5351d7c79Además, Adrian creó una demostración que facilita la comprensión de la diferencia entre las propiedades lógicas y direccionales.
Soporte del navegador
El soporte del navegador es bastante bueno para las propiedades de relleno, margen y alineación de texto. Sin embargo, todavía no es suficiente para las propiedades de radio de borde. A continuación se muestra una tabla de soporte del sitio
Can I Use :


Aunque el soporte aún no es perfecto (y nunca lo será), le aconsejo que comience a usar propiedades lógicas con fallos en este momento. Por ejemplo
.input--search { padding-left: 1rem; padding-right: 2.5rem; padding-inline-start: 1rem; padding-inline-end: 2.5rem; }
Además, puede usar el
complemento lógico PostCSS , que agrega un respaldo para cada propiedad lógica utilizada.
Convenciones de nomenclatura CSS
Evite dar nombres de clases CSS que estén adjuntos a sus elementos. Utilice nombres que se puedan extraer en componentes reutilizables. Considere el siguiente ejemplo:
<div class="c-section"> <p><a href="#" class="see-link">See more</a></p> </div> <div class="c-section"> <p><a href="#" class="see-link">Learn more</a></p> </div>
Los enlaces son iguales en ambos bloques, pero sus nombres son diferentes. En el segundo bloque, la clase see-link no tiene sentido. Un buen nombre podría ser c-link. El prefijo c– se sustituye por componentes; adopté este método del marco ITCSS.
Ahora que comprende la idea, también podemos aplicar esto al estilo RTL. El siguiente ejemplo muestra una sección con dos hijos.

En lugar de dar nombres a los elementos como .c-page-header__left y .c-page-header__right, los llamo .c-page-header__start y .c-page-header__end. Esto está más orientado al futuro y no implica que el sitio se cree solo en modo LTR o RTL.
Herramientas de automatización
Existen excelentes herramientas para facilitar el trabajo con marcado LTR y RTL.
1. Bi-App-Sass
Bi-App-Sass de Anas Nakava le permite escribir una versión de estilos que se compila en dos hojas de estilo diferentes: una para LRT y otra para marcado RTL.
Esta herramienta puede ser útil para grandes proyectos.
Como resultado, puede haber muchas hojas de estilo para cada dirección de escritura. Considere el siguiente ejemplo: .elem { display: flex; @include margin-left(10px); @include border-right(2px solid #000); }
El código CSS resultante puede ser el siguiente.Archivo App-ltr.css: .elem { display: flex; margin-left: 10px; border-right: 2px solid #000; }
Archivo App-rtl.css: .elem { display: flex; margin-right: 10px; border-left: 2px solid #000; }
Sin embargo, tenga en cuenta que el último compromiso con el repositorio en GitHub fue hace cuatro años (noviembre de 2015).2. RTLCSS
RTLCSS por Mohamed Jonas es un marco para convertir hojas de estilo LTR en RTL.La diferencia entre esta herramienta es que se aplica a una versión ya ensamblada del archivo CSS. Por ejemplo, si tiene más de 50 componentes Sass en su proyecto, RTLCSS es útil para analizar un archivo CSS compilado y crear una versión RTL a partir de él.Ejemplos prácticos
Encabezado del sitio
Específicamente hice un diseño para mostrar qué enfoque estoy usando para implementar la versión RTL del marcado.
Comencemos con los componentes del encabezado. Para implementar esto correctamente en el código, describí esquemáticamente su estructura general. Tenga en cuenta que dividí el encabezado en la sección principal y subsección. Además, se agregaron clases de inicio y finalización para elementos secundarios.
.header__main, .header__sub { display: flex; justify-content: space-between; }
Debido a que la operación de CSS Flexbox tiene en cuenta la dirección especificada en la página, como se explicó anteriormente en esta guía, se expandirá automáticamente cuando se use el marcado RTL.
El siguiente punto es la línea divisoria entre el logotipo y la navegación. Al principio pensé en usar border-right. Funciona, pero no es perfecto. Es mejor usar un pseudo-elemento, ya que se expandirá después de la dirección de la página.
.c-brand:after { content: ""; display: inline-block; vertical-align: middle; width: 3px; height: 38px; border-radius: 5px; background: #e4e4e4; margin-inline-start: 1.25rem; }
Aquí está el resultado actual:
A continuación, trabajaré con el componente de sección (el que está en la subsección de encabezado y contiene nombres y contadores). A continuación se muestra un diseño de cómo debería verse este componente en LTR.
A primera vista, esto puede parecer simple, pero en realidad requiere especificar varias propiedades de relleno y margen. Aquí hay un diseño que demuestra esto:
.topics-heading { margin-inline-end: 1.5rem; } .topics-list { margin-inline-end: 1rem; } .c-topic { padding-inline-start: 0.5rem; } .c-topic:not(:last-child) { margin-inline-end: 10px; } .c-topic__counter { margin-inline-start: 1rem; }
Como puede ver, uso propiedades booleanas CSS en lugar de valores izquierdo y derecho.El siguiente paso es el enlace "Ver todo". Presta atención a la flecha al final. Ella debe tener el siguiente comportamiento:- Al desplazarse, el color de la flecha debería cambiar.
- Al pasar el ratón, la animación debe aplicarse a la flecha.
Decidí usar el SVG incorporado para esta tarea. Cuando configuré la flecha para traducir, pensé en RTL. No hay propiedades lógicas adecuadas para esta situación y necesito considerar otra solución. La opción con margen cambiante surgió. .c-link svg { margin-inline-start: 4px; transition: 0.15s ease-in; } .c-link:hover svg { margin-inline-start: 8px; }
Aunque animar los márgenes no afecta muy bien el rendimiento, todavía funciona. Otra solución es determinar la dirección de la página e indicar, en base a esto, la dirección correspondiente para el desplazamiento .c-link:hover svg { transform: translateX(6px); } .c-header[dir="rtl"] .c-link svg { transform: scaleX(-1); } .c-header[dir="rtl"] .c-link:hover svg { transform: scaleX(-1) translateX(6px); }
Tenga en cuenta que para la dirección de la página RTL, agregué scaleX (-1) para expandir el icono horizontalmente. También puede usar rotar (180 grados), pero la opción de escala me parece más simple.
Luego viene el campo de búsqueda. Los requisitos son los siguientes:- El icono de búsqueda debe aparecer al final del campo.
- La ubicación del icono de búsqueda debe ser dinámica.
.c-input--search { background-image: url("data:image/svg+xml..."); background-position: right 6px center; } .c-header[dir="rtl"] .c-input--search { background-image: url("data:image/svg+xml..."); background-position: right 6px center; }
Además, cuando el usuario escribe el texto en este campo, el texto no debe superponerse al icono. Para evitar esto, agregue relleno a ambos lados del campo.
El resultado es el siguiente marcado para los modos LTR y RTL:
El siguiente es el menú móvil. Para designarlo, usaré un icono de hamburguesa. La ubicación del icono cambiará según la dirección (LTR o RTL). Lo mismo ocurre con la dirección de la animación de desplazamiento.
Puedes ver la demo en CodePenGratitud
Un agradecimiento especial a mi esposa Kholoud por su continuo apoyo y la lectura múltiple del manual. Gracias también a Adebiyi Adedotun Lukman y Šime Vidas por sus increíbles comentarios.