Cómo animar elementos al hacer scroll sin JavaScript

Animar elementos al hacer scroll sin JavaScript es una de esas técnicas que hace unos años parecía depender casi siempre de librerías externas, detectores de intersección, escuchas de eventos o soluciones personalizadas con scroll. Sin embargo, CSS ha avanzado mucho, y hoy podemos crear animaciones vinculadas al desplazamiento de una página de forma mucho más declarativa, limpia y cercana al propio lenguaje de estilos.

Cuando hablamos de animaciones scroll CSS sin JavaScript, no nos referimos únicamente a “hacer aparecer cosas con un poco de opacidad”. Hablamos de barras de progreso, textos que entran suavemente en pantalla, imágenes que se revelan al hacer scroll, secciones que se desplazan con efecto parallax moderado y componentes que reaccionan al avance del usuario dentro de una página.

La gran ventaja es clara: podemos mejorar la experiencia visual sin añadir complejidad innecesaria al proyecto. Eso sí, también conviene ser realistas. Las animaciones basadas en scroll con CSS moderno son muy potentes, pero todavía requieren una estrategia de compatibilidad progresiva. En otras palabras: podemos usarlas, pero debemos prepararlas para que la web siga funcionando correctamente aunque el navegador no soporte todas las propiedades más recientes.

En este artículo vamos a ver cómo animar al hacer scroll con CSS, qué propiedades modernas entran en juego, cuándo conviene usarlas, cómo plantear alternativas seguras y qué buenas prácticas deberías aplicar para que tus animaciones sean bonitas, accesibles y sostenibles.

Qué significa animar al hacer scroll sin JavaScript

Animar al hacer scroll significa que una animación no depende únicamente del paso del tiempo, como ocurre con una animación CSS tradicional. En una animación clásica, defines unos @keyframes, asignas una duración y el navegador reproduce la animación durante un número determinado de segundos.

Por ejemplo:

.card {
  animation: fade-in 0.8s ease both;
}

@keyframes fade-in {
  from {
    opacity: 0;
    transform: translateY(24px);
  }

  to {
    opacity: 1;
    transform: translateY(0);
  }
}

Este código anima la tarjeta cuando se carga o cuando aparece en el flujo normal del documento, pero no está realmente vinculado al scroll. La animación ocurre por tiempo.

En cambio, una scroll animation CSS conecta el progreso de la animación con el desplazamiento del usuario. Es decir, la animación avanza, retrocede o se completa según la posición de scroll.

Esto permite crear efectos como:

  • Barras de lectura que se llenan al avanzar por un artículo.
  • Elementos que aparecen cuando entran en el viewport.
  • Imágenes que se revelan progresivamente.
  • Títulos que se desplazan o escalan de forma suave.
  • Secciones que ganan opacidad a medida que el usuario baja.

La diferencia principal es conceptual: ya no pensamos en una duración fija, sino en una relación entre posición de scroll y progreso de animación.

La base técnica: CSS Scroll-Driven Animations

Las animaciones al hacer scroll sin JavaScript se apoyan en lo que se conoce como CSS Scroll-Driven Animations. Este conjunto de propiedades permite asociar una animación CSS a una línea temporal basada en el desplazamiento.

En lugar de utilizar únicamente la línea temporal tradicional del documento, CSS puede usar una línea temporal derivada del scroll. Esto abre la puerta a animaciones declarativas, sin necesidad de escuchar eventos scroll desde JavaScript.

Scroll timeline y view timeline

Dentro de este enfoque hay dos ideas importantes:

Scroll timeline

Una scroll timeline vincula la animación al progreso de desplazamiento de un contenedor. Es útil, por ejemplo, para crear una barra de progreso de lectura que se rellena desde el inicio hasta el final de la página.

En este caso, la animación responde al avance general del scroll.

View timeline

Una view timeline vincula la animación a la visibilidad de un elemento dentro del viewport. Es decir, el elemento puede empezar a animarse cuando entra en pantalla y completar la animación cuando alcanza una determinada zona visible.

Este enfoque es especialmente útil para animar elementos al hacer scroll CSS sin tener que detectar manualmente si el elemento está visible.

Ejemplo básico: animar una tarjeta al entrar en pantalla

Vamos a partir de un ejemplo sencillo. Imagina una serie de tarjetas dentro de una página de servicios, portfolio o blog. Queremos que cada tarjeta aparezca suavemente cuando el usuario llega a esa zona.

HTML de ejemplo

<section class="features">
  <article class="feature-card">
    <h2>Diseño responsive</h2>
    <p>Interfaces adaptadas a cualquier tamaño de pantalla.</p>
  </article>

  <article class="feature-card">
    <h2>Animaciones suaves</h2>
    <p>Microinteracciones cuidadas para mejorar la experiencia.</p>
  </article>

  <article class="feature-card">
    <h2>CSS moderno</h2>
    <p>Soluciones visuales limpias sin depender siempre de JavaScript.</p>
  </article>
</section>

CSS con animation-timeline: view()

.feature-card {
  opacity: 0;
  transform: translateY(40px);
  animation: reveal-card linear both;
  animation-timeline: view();
  animation-range: entry 10% cover 35%;
}

@keyframes reveal-card {
  from {
    opacity: 0;
    transform: translateY(40px);
  }

  to {
    opacity: 1;
    transform: translateY(0);
  }
}

Con este código, cada tarjeta se anima en relación con su entrada en pantalla. La propiedad animation-timeline: view() indica que la animación dependerá de la visibilidad del propio elemento.

La propiedad animation-range define en qué tramo de esa visibilidad empieza y termina la animación. En este caso, la tarjeta comienza a animarse cuando entra parcialmente en pantalla y completa su transición cuando ya ocupa una parte más clara del viewport.

Este patrón es ideal para crear una sensación de progresión sin convertir la página en un espectáculo excesivo. La animación acompaña al contenido, no compite con él.

Barra de progreso de lectura solo con CSS

Una de las aplicaciones más útiles de las animaciones vinculadas al scroll es la barra de progreso de lectura. Es habitual verla en artículos largos, guías técnicas o páginas de documentación.

La idea es sencilla: una barra fija en la parte superior de la página se va rellenando a medida que el usuario avanza.

HTML

<div class="reading-progress"></div>

CSS

.reading-progress {
  position: fixed;
  top: 0;
  left: 0;
  z-index: 999;
  width: 100%;
  height: 4px;
  transform-origin: left;
  transform: scaleX(0);
  animation: reading-progress linear both;
  animation-timeline: scroll(root);
}

@keyframes reading-progress {
  to {
    transform: scaleX(1);
  }
}

Aquí usamos animation-timeline: scroll(root), que vincula la animación al scroll del documento raíz. La barra empieza con scaleX(0) y termina con scaleX(1), creando una sensación de avance visual muy clara.

Este tipo de detalle mejora la orientación del usuario. En artículos extensos, una barra de progreso puede ayudar a entender cuánto contenido queda por leer sin añadir textos, porcentajes ni componentes adicionales.

Animaciones de revelado con imagen y texto

Otra técnica muy interesante consiste en revelar imágenes o bloques visuales a medida que entran en pantalla. Este efecto puede funcionar muy bien en portfolios, landing pages, páginas de producto o artículos visuales.

HTML

<figure class="image-reveal">
  <img src="proyecto-web.jpg" alt="Vista previa de un proyecto web responsive">
</figure>

CSS

.image-reveal {
  overflow: hidden;
}

.image-reveal img {
  display: block;
  width: 100%;
  transform: scale(1.15);
  opacity: 0;
  animation: reveal-image linear both;
  animation-timeline: view();
  animation-range: entry 15% cover 45%;
}

@keyframes reveal-image {
  to {
    transform: scale(1);
    opacity: 1;
  }
}

En este caso combinamos opacity y transform, dos propiedades especialmente recomendables para animaciones porque suelen ser más eficientes que modificar dimensiones, márgenes o posiciones que obliguen al navegador a recalcular el layout.

El resultado es una imagen que aparece suavemente mientras reduce su escala. Es un efecto elegante, fácil de entender y suficientemente discreto para no saturar la experiencia.

Hacer que el texto acompañe al movimiento

También podemos aplicar una animación similar a los textos:

.scroll-title {
  opacity: 0;
  transform: translateY(32px);
  animation: reveal-title linear both;
  animation-timeline: view();
  animation-range: entry 20% cover 40%;
}

@keyframes reveal-title {
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

Este patrón funciona muy bien en encabezados de sección. La clave está en no abusar. Si cada párrafo, imagen, botón y tarjeta de una página se anima, la experiencia puede volverse cansada. La animación debe tener una intención: guiar, jerarquizar o reforzar una transición visual.

Compatibilidad: cómo usar CSS moderno sin romper la experiencia

Aquí conviene hacer una pausa importante. Aunque las animaciones de scroll con CSS son una herramienta muy prometedora, no deberías construir una experiencia que dependa al cien por cien de ellas.

La mejor estrategia es aplicar mejora progresiva. Es decir, primero defines un diseño funcional y accesible para todos los navegadores. Después, añades la animación solo cuando el navegador soporte las propiedades necesarias.

Usar @supports

Podemos envolver nuestras animaciones modernas dentro de una regla @supports:

.feature-card {
  opacity: 1;
  transform: none;
}

@supports (animation-timeline: view()) {
  .feature-card {
    opacity: 0;
    transform: translateY(40px);
    animation: reveal-card linear both;
    animation-timeline: view();
    animation-range: entry 10% cover 35%;
  }
}

Este enfoque es mucho más seguro. Por defecto, la tarjeta se muestra normalmente. Si el navegador soporta animation-timeline: view(), entonces se aplica la animación.

Esto evita uno de los errores más peligrosos: dejar elementos con opacity: 0 en navegadores que no soportan la animación. Si eso ocurre, el contenido podría quedar invisible para parte de los usuarios.

Orden correcto de las propiedades

Un detalle importante: si usas la propiedad abreviada animation, declara animation-timeline después. Algunas propiedades abreviadas pueden reiniciar valores relacionados con la animación, por lo que conviene mantener un orden claro:

.element {
  animation: reveal linear both;
  animation-timeline: view();
}

Evita hacer esto:

.element {
  animation-timeline: view();
  animation: reveal linear both;
}

Aunque parezca un detalle menor, este tipo de orden puede marcar la diferencia entre una animación que funciona y otra que no se aplica como esperabas.

Buenas prácticas para animar al hacer scroll con CSS

Animar con scroll no consiste en añadir movimiento porque sí. Una buena animación tiene una función. Debe aportar claridad, ritmo o contexto.

Prioriza opacity y transform

Cuando sea posible, anima propiedades como:

  • opacity
  • transform: translate
  • transform: scale
  • transform: rotate

Estas propiedades suelen ser más adecuadas para animaciones fluidas porque no modifican directamente el flujo del documento.

En cambio, conviene evitar animar propiedades como:

  • width
  • height
  • margin
  • top
  • left
  • padding

No significa que estén prohibidas, pero pueden generar más trabajo de renderizado y afectar al rendimiento si se usan en exceso.

No conviertas cada scroll en una feria visual

Una página llena de animaciones puede parecer moderna durante los primeros segundos, pero cansar rápidamente. Lo recomendable es elegir puntos clave:

  • La entrada de una sección importante.
  • Una imagen destacada.
  • Una barra de progreso.
  • Un bloque de llamada a la acción.
  • Una transición entre partes del contenido.

El movimiento debe acompañar al usuario, no interrumpirlo.

Cuida la duración percibida

En las animaciones scroll CSS sin JavaScript, la duración no se mide igual que en una animación temporal. Depende del tramo de scroll asignado. Por eso animation-range es tan importante.

Un rango demasiado corto puede hacer que el efecto sea brusco. Un rango demasiado largo puede hacer que la animación parezca lenta o imprecisa.

Una buena regla inicial es probar rangos como:

animation-range: entry 10% cover 35%;

O bien:

animation-range: entry 20% cover 50%;

Después ajusta según el tipo de elemento, el ritmo de la página y la importancia visual del contenido.

Accesibilidad: respeta prefers-reduced-motion

No todas las personas disfrutan de las animaciones. Para algunos usuarios, ciertos movimientos pueden resultar molestos, distraer o incluso provocar incomodidad. Por eso es fundamental respetar la preferencia del sistema mediante prefers-reduced-motion.

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    scroll-behavior: auto !important;
  }
}

También puedes ser más específica y desactivar solo las animaciones vinculadas al scroll:

@media (prefers-reduced-motion: reduce) {
  .feature-card,
  .image-reveal img,
  .scroll-title {
    animation: none;
    opacity: 1;
    transform: none;
  }
}

Este segundo enfoque suele ser más controlado. Permite mantener la interfaz estable y evita que el contenido dependa del movimiento para ser comprensible.

La accesibilidad no debería verse como una capa final, sino como parte del diseño de la animación desde el principio.

CSS sin JavaScript no significa CSS sin estrategia

Usar CSS sin JavaScript para animaciones de scroll tiene muchas ventajas. Reduce dependencias, simplifica el mantenimiento y permite escribir efectos visuales de forma más declarativa. Pero eso no significa que debamos aplicarlo sin criterio.

Hay casos en los que CSS será suficiente:

  • Efectos de aparición simples.
  • Barras de progreso.
  • Revelados visuales.
  • Animaciones decorativas no críticas.
  • Microinteracciones asociadas a la visibilidad del elemento.

Pero también hay casos en los que JavaScript puede seguir siendo necesario:

  • Animaciones con lógica compleja.
  • Estados dependientes de datos.
  • Sincronización con componentes interactivos.
  • Experiencias donde la animación modifica comportamiento real.
  • Compatibilidad estricta con navegadores antiguos.

La clave está en elegir la herramienta adecuada. Si el efecto es visual, progresivo y no crítico, CSS puede ser una opción excelente. Si la animación forma parte de una lógica más compleja, quizá JavaScript siga teniendo sentido.

Ejemplo completo: sección animada al hacer scroll

Veamos un ejemplo más completo que combina buenas prácticas, mejora progresiva y accesibilidad.

HTML

<section class="services-section">
  <header class="section-header">
    <p class="eyebrow">Servicios web</p>
    <h2>Interfaces modernas con CSS limpio y eficiente</h2>
    <p>
      Creamos experiencias visuales cuidadas, accesibles y adaptadas
      a diferentes dispositivos.
    </p>
  </header>

  <div class="services-grid">
    <article class="service-card">
      <h3>Diseño responsive</h3>
      <p>Componentes pensados para funcionar en móvil, tablet y escritorio.</p>
    </article>

    <article class="service-card">
      <h3>Animaciones CSS</h3>
      <p>Microinteracciones suaves que mejoran la experiencia sin sobrecargarla.</p>
    </article>

    <article class="service-card">
      <h3>Optimización visual</h3>
      <p>Interfaces rápidas, claras y alineadas con los objetivos del proyecto.</p>
    </article>
  </div>
</section>

CSS

.services-section {
  padding: 6rem 1.5rem;
}

.section-header,
.service-card {
  opacity: 1;
  transform: none;
}

.services-grid {
  display: grid;
  gap: 1.5rem;
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
}

.service-card {
  padding: 1.5rem;
  border-radius: 1rem;
  background: #ffffff;
  box-shadow: 0 16px 40px rgb(0 0 0 / 0.08);
}

@supports (animation-timeline: view()) {
  .section-header {
    opacity: 0;
    transform: translateY(32px);
    animation: reveal-block linear both;
    animation-timeline: view();
    animation-range: entry 10% cover 35%;
  }

  .service-card {
    opacity: 0;
    transform: translateY(40px);
    animation: reveal-block linear both;
    animation-timeline: view();
    animation-range: entry 15% cover 40%;
  }
}

@keyframes reveal-block {
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

@media (prefers-reduced-motion: reduce) {
  .section-header,
  .service-card {
    animation: none;
    opacity: 1;
    transform: none;
  }
}

Este ejemplo tiene tres puntos importantes. Primero, el contenido es visible por defecto. Segundo, la animación solo se aplica si el navegador la soporta. Tercero, se respeta la preferencia de reducción de movimiento.

Es una base mucho más sólida que limitarse a copiar una animación vistosa sin pensar en compatibilidad, accesibilidad o mantenimiento.

Errores comunes al crear animaciones scroll CSS sin JavaScript

Aunque la técnica es relativamente sencilla, hay varios errores frecuentes que conviene evitar.

Dejar el contenido oculto por defecto

Si defines opacity: 0 fuera de @supports, puedes provocar que el contenido quede invisible en navegadores sin soporte. Es mejor que el estado base sea visible y que la animación se añada como mejora.

Animar demasiadas propiedades

Una animación que combina opacidad, escala, desplazamiento, blur, rotación y cambios de tamaño puede resultar pesada y confusa. Cuanto más simple sea el movimiento, más profesional suele sentirse.

No probar en dispositivos reales

Las animaciones pueden verse muy bien en escritorio y resultar incómodas en móvil. El ritmo de scroll, el tamaño del viewport y el rendimiento cambian mucho según el dispositivo.

Ignorar la accesibilidad

No respetar prefers-reduced-motion es un error importante. Las animaciones deben poder reducirse o eliminarse sin que la página pierda contenido ni sentido.

FAQs sobre animar elementos al hacer scroll sin JavaScript

¿Se puede animar al hacer scroll solo con CSS?

Sí, actualmente CSS permite crear animaciones vinculadas al scroll mediante propiedades como animation-timeline, scroll() y view(). Esto permite construir efectos visuales sin escuchar eventos de scroll con JavaScript. Aun así, conviene aplicar mejora progresiva porque no todos los navegadores ofrecen el mismo nivel de soporte.

¿Es mejor usar CSS o JavaScript para animaciones de scroll?

Depende del caso. Para efectos visuales sencillos, revelados de contenido, barras de progreso o animaciones decorativas, CSS puede ser una solución más limpia y mantenible. Para interacciones complejas, estados dinámicos o lógica avanzada, JavaScript puede seguir siendo necesario.

¿Las animaciones de scroll afectan al rendimiento?

Pueden afectar si se usan mal. Para mejorar el rendimiento, conviene animar propiedades como transform y opacity, evitar animaciones excesivas y probar en dispositivos reales. También es importante no depender de animaciones críticas para mostrar contenido esencial.

Reflexión final: animar menos, pero animar mejor

Animar elementos al hacer scroll sin JavaScript es una posibilidad muy atractiva para quienes trabajamos con CSS moderno. Nos permite crear experiencias más dinámicas, reducir dependencias y aprovechar mejor las capacidades nativas del navegador.

Sin embargo, la pregunta importante no es solo “¿puedo animarlo?”, sino “¿esta animación mejora realmente la experiencia?”. Una buena animación no debería estar para presumir de técnica, sino para acompañar la lectura, reforzar la jerarquía visual y hacer que la interfaz resulte más clara.

Las animaciones scroll CSS sin JavaScript tienen mucho potencial, especialmente cuando se combinan con accesibilidad, mejora progresiva y sentido del diseño. Usadas con moderación, pueden transformar una página estática en una experiencia más fluida y memorable. Usadas sin criterio, pueden convertirse en ruido.

Por eso, la mejor recomendación es empezar de forma sencilla: una barra de progreso, una tarjeta que aparece suavemente, una imagen que se revela al entrar en pantalla. A partir de ahí, prueba, mide, ajusta y elimina todo lo que no aporte valor.

En CSS, como en diseño, muchas veces la elegancia está en saber cuándo moverse y cuándo quedarse quieto.

UX en email marketing: claridad antes que decoración

El UX en email marketing suele quedar en segundo plano porque muchas veces se habla antes de diseño visual, colores, animaciones, banners o llamadas a la acción llamativas. Sin embargo, una newsletter no funciona mejor por estar más decorada, sino por ser más clara.

El usuario abre un correo en un contexto muy concreto: tiene poco tiempo, suele estar revisando varios mensajes a la vez y decide en pocos segundos si ese email merece su atención o si debe eliminarlo, archivarlo o ignorarlo. Por eso, cuando hablamos de diseño de newsletters, no deberíamos empezar preguntando “¿cómo lo hacemos más bonito?”, sino “¿cómo lo hacemos más fácil de entender?”.

La estética importa, claro. Una buena composición visual transmite profesionalidad, refuerza la marca y puede mejorar la percepción del contenido. Pero si la decoración compite con el mensaje, el diseño deja de ayudar y empieza a molestar.

En email marketing, la experiencia de usuario no se mide solo por si el correo “se ve bien”. También importa si se entiende rápido, si carga correctamente, si se adapta al móvil, si el botón principal es evidente, si el texto se puede leer sin esfuerzo y si la persona sabe qué hacer después de abrirlo.

En otras palabras: un buen email no es el que más elementos tiene, sino el que mejor guía la atención.

Qué significa realmente UX en email marketing

La UX, o experiencia de usuario, aplicada al email marketing consiste en diseñar correos pensando en cómo las personas los leen, interpretan y utilizan. No se trata únicamente de organizar módulos bonitos, sino de construir una experiencia breve, clara y útil dentro de una bandeja de entrada saturada.

Una newsletter no es una landing page completa ni una revista digital. Tiene un espacio limitado, una atención limitada y unas condiciones técnicas bastante particulares. Algunos clientes de correo interpretan HTML y CSS de manera diferente, y no todas las propiedades modernas funcionan igual en Gmail, Outlook, Apple Mail u otros entornos.

Por eso, antes de plantear un diseño demasiado ambicioso, conviene entender bien qué partes de CSS funcionan realmente en email marketing. Esta base técnica ayuda a tomar mejores decisiones visuales y evita depender de efectos que pueden romperse en determinados clientes de correo.

El UX en email marketing debe equilibrar tres capas:

  • La capa estratégica, que responde a qué queremos conseguir con el correo.
  • La capa de contenido, que define qué necesita entender la persona.
  • La capa visual y técnica, que decide cómo se presenta ese mensaje para que sea legible, accesible y funcional.

Cuando estas tres capas trabajan juntas, el email se siente natural. Cuando se diseñan por separado, aparecen los problemas: newsletters preciosas pero confusas, campañas con demasiados botones, emails con imágenes enormes que no explican nada si no cargan, textos imposibles de escanear o llamadas a la acción enterradas entre bloques decorativos.

La claridad como principio central del diseño de newsletters

La claridad no significa hacer diseños aburridos. Significa eliminar fricción. Un email claro permite que la persona entienda en segundos quién escribe, por qué le escribe, qué le ofrece y qué puede hacer a continuación.

En una newsletter, la claridad empieza incluso antes de abrir el correo: en el asunto, el preheader y el remitente. Si esos tres elementos no generan confianza o no explican bien el contenido, el diseño interior ni siquiera llega a participar.

Pero una vez dentro, la claridad depende sobre todo de la jerarquía visual, la estructura del mensaje y la relación entre texto, imagen y acción.

El usuario no lee: escanea

En email marketing, muchas personas no leen de principio a fin. Primero escanean. Buscan señales rápidas: títulos, palabras destacadas, botones, precios, fechas, beneficios o imágenes que les indiquen si el contenido les interesa.

Por eso, una newsletter debe diseñarse como un recorrido de lectura guiado. El primer bloque debería responder a la pregunta principal: “¿Qué me aporta este email?”. Si la respuesta tarda demasiado en aparecer, el usuario se va.

Aquí entra una idea clave: la decoración nunca debería retrasar la comprensión. Un fondo bonito, una ilustración elaborada o una composición muy editorial pueden funcionar si acompañan al mensaje. Pero si obligan a la persona a esforzarse para encontrar la información importante, están trabajando en contra del objetivo del email.

Jerarquía visual: decidir qué importa primero

Una buena jerarquía visual no consiste en hacer todo grande, brillante o colorido. Consiste en decidir qué elemento merece más atención y qué elementos deben acompañarlo.

En una newsletter básica, la jerarquía suele apoyarse en varios elementos: titular principal, texto introductorio, llamada a la acción y contenido secundario. Cada uno cumple una función distinta y debería tener un peso visual acorde a su importancia.

Titular principal

El titular debe ser claro, concreto y útil. Mejor “Aprende a crear emails responsive sin romper el diseño” que “Una nueva forma de comunicar”. El segundo puede sonar más elegante, pero el primero explica mucho mejor el valor.

Texto introductorio

El texto inicial debe ampliar la promesa del titular sin repetirse demasiado. Aquí conviene evitar párrafos largos. Un email no es el lugar ideal para presentar una reflexión interminable antes de mostrar el contenido principal.

CTA principal

El botón o enlace principal debe destacar visualmente y tener un texto accionable. “Ver guía”, “Descargar plantilla” o “Reservar plaza” suelen funcionar mejor que un genérico “Haz clic aquí”.

Además, desde el punto de vista de accesibilidad y usabilidad, los enlaces deben tener sentido por sí mismos. Un texto como “haz clic aquí” obliga al usuario a depender del contexto, mientras que “descargar la plantilla de newsletter” explica mejor qué va a ocurrir.

Elementos secundarios

Imágenes, iconos, separadores, etiquetas o bloques complementarios deben ayudar a ordenar la información. Si no aportan claridad, probablemente sobran.

Decoración visual: cuándo ayuda y cuándo estorba

La decoración no es enemiga de la UX. El problema aparece cuando la decoración toma decisiones que deberían pertenecer al contenido y a la usabilidad.

Un buen recurso visual puede hacer que una campaña sea más memorable. Una ilustración puede reforzar la personalidad de marca. Un color puede dirigir la mirada hacia una acción concreta. Una composición cuidada puede transmitir calma, energía o exclusividad.

Pero en diseño de newsletters, cada elemento visual debe pasar una prueba sencilla: “¿Ayuda a entender mejor el mensaje?”. Si la respuesta es no, quizá sea solo ruido.

Señales de que tu newsletter está demasiado decorada

Una newsletter empieza a perder claridad cuando el primer pantallazo está ocupado por una imagen enorme sin texto útil, cuando hay varios botones compitiendo entre sí o cuando el usuario no sabe si el objetivo es leer, comprar, registrarse o descargar algo.

También hay señales más sutiles: colores decorativos que reducen el contraste, iconos bonitos pero poco comprensibles, demasiadas secciones con el mismo peso visual o mensajes importantes escondidos debajo de banners, frases inspiracionales y elementos de marca.

El diseño visual debe crear un camino, no un laberinto. Si todo grita, nada destaca.

La marca no debería estar por encima del mensaje

Es habitual querer que una newsletter “respire marca”: colores corporativos, tipografías reconocibles, estilo gráfico propio y tono de voz coherente. Todo eso es positivo. Pero la identidad visual no debe convertirse en una barrera.

Un email puede ser muy reconocible sin llenar cada módulo de elementos decorativos. A veces basta con una cabecera limpia, una paleta consistente, buenos espacios en blanco, botones coherentes y una voz clara. La marca se construye también desde la facilidad de uso.

Legibilidad: el corazón silencioso de una buena newsletter

La legibilidad es uno de los pilares más importantes del UX en email marketing. Si el texto cuesta leerlo, el email falla, aunque el diseño sea atractivo.

La legibilidad depende de muchos factores: tamaño de fuente, longitud de línea, contraste, espaciado, alineación, estructura de párrafos y cantidad de texto. En móvil, estos factores se vuelven todavía más críticos.

Por eso, una newsletter no debería diseñarse como si se fuera a leer siempre en una pantalla grande y tranquila. Muchas aperturas se producen desde el móvil, en momentos de interrupción o mientras la persona hace otras tareas.

Tamaño de letra y espaciado

Un error común es usar tamaños demasiado pequeños para intentar meter más contenido. Sin embargo, cuando el texto se ve denso o incómodo, la persona no se esfuerza más: simplemente abandona.

Como regla práctica, el cuerpo del texto debería tener un tamaño cómodo y suficiente interlineado. Los párrafos cortos funcionan mejor que los bloques densos. Las listas ayudan a escanear, pero tampoco conviene abusar de ellas.

La lectura en email debe sentirse ligera. Esto no significa escribir menos siempre, sino estructurar mejor.

Alineación y ancho del contenido

El texto centrado puede funcionar en titulares breves, pero resulta incómodo en párrafos largos. Para cuerpos de texto, la alineación izquierda suele facilitar la lectura, especialmente en emails informativos o educativos.

También conviene controlar el ancho del contenido. Una línea demasiado larga cansa; una demasiado corta rompe el ritmo. En email, donde el ancho suele estar limitado, esto se puede gestionar con contenedores equilibrados y buenos márgenes internos.

Negritas con intención

Las negritas ayudan a destacar ideas clave, pero si se usan en exceso pierden fuerza. Lo ideal es resaltar conceptos que ayuden al usuario a escanear el mensaje: beneficios, advertencias, pasos importantes o ideas de valor.

La cursiva, en cambio, puede reservarse para matices, términos en otro idioma o énfasis suave. No debería usarse para grandes bloques de texto, porque puede reducir la legibilidad.

UX y accesibilidad en emails: no son temas separados

La accesibilidad no es un añadido técnico que se revisa al final. Forma parte de la experiencia de usuario. Un email accesible es más usable para todo el mundo: personas que usan lectores de pantalla, personas con baja visión, usuarios que leen en exteriores con mucho brillo, personas con fatiga visual o simplemente alguien que abre el correo deprisa desde el móvil.

Si estás trabajando una estrategia de newsletters más cuidada, también merece la pena revisar cómo afectan el contraste, la jerarquía y los lectores de pantalla al resultado final. Puedes profundizar en este tema en el artículo sobre emails accesibles: contraste, jerarquía y lectores de pantalla.

Imágenes con sentido, no como único soporte

Un error frecuente en email marketing es colocar información importante dentro de una imagen: descuentos, fechas, titulares, condiciones o llamadas a la acción. Esto genera varios problemas.

Primero, si la imagen no carga, el mensaje desaparece. Segundo, los lectores de pantalla no pueden interpretar el texto incrustado en la imagen si no existe una alternativa adecuada. Tercero, el usuario no puede seleccionar, copiar o ampliar ese texto con facilidad.

Las imágenes deberían reforzar el mensaje, no sustituirlo. Si una promoción depende de un banner, conviene repetir la información esencial en texto HTML real.

Texto alternativo útil

El atributo alt no debería rellenarse de forma automática ni convertirse en una lista de palabras clave. Debe describir la función o el contenido de la imagen según el contexto.

Si la imagen es decorativa, puede tener un alt vacío. Si comunica información, debe explicarla. Si funciona como enlace, el texto alternativo debería indicar la acción o destino.

Orden lógico de lectura

Un email visualmente atractivo puede ser confuso para tecnologías asistivas si el orden del código no sigue el orden lógico del contenido. Esto ocurre cuando se maquetan bloques pensando solo en la composición visual.

La pregunta útil es: “Si este email se leyera de arriba abajo sin estilos, ¿seguiría teniendo sentido?”. Si la respuesta es sí, la base de UX y accesibilidad es mucho más sólida.

Diseño responsive: claridad también en pantallas pequeñas

El responsive en email no debería entenderse solo como “que no se rompa en móvil”. La verdadera pregunta es: “¿Sigue siendo claro y usable en móvil?”.

Un diseño puede adaptarse al ancho de pantalla y aun así ofrecer una mala experiencia si los botones son pequeños, los textos quedan demasiado juntos o el contenido principal aparece demasiado abajo.

Este punto es especialmente importante porque el desarrollo de emails tiene sus propias limitaciones. Si quieres profundizar en la parte más técnica, te recomiendo leer también cómo hacer emails responsive sin volverte loca con tablas HTML.

Mobile-first mental

Aunque el diseño se construya técnicamente con tablas o con herramientas como MJML, la mentalidad debería ser mobile-first. Esto implica priorizar botones grandes y fáciles de pulsar, titulares directos, imágenes optimizadas, bloques apilables, texto breve y espacios suficientes entre elementos interactivos.

Cuando se diseña primero para móvil, es más fácil detectar qué sobra. Si un bloque ocupa demasiado, si una imagen desplaza el mensaje principal o si el botón queda enterrado, el problema aparece enseguida.

En cambio, cuando se diseña primero para escritorio, es habitual acabar adaptando a móvil una estructura demasiado pesada.

El CTA debe sobrevivir al responsive

El botón principal no debería perderse en móvil. Debe aparecer pronto, tener un tamaño cómodo y un texto claro.

Además, no conviene colocar demasiadas llamadas a la acción distintas en un mismo email, especialmente si todas parecen igual de importantes. Una newsletter con varios objetivos suele convertirse en una newsletter sin objetivo.

Lo más recomendable es definir una acción principal clara y, si hace falta, añadir acciones secundarias visualmente menos protagonistas.

Contenido y microcopy: UX también es escribir mejor

El diseño no puede arreglar un mensaje confuso. El UX en email marketing depende mucho del copy: titulares, subtítulos, botones, enlaces, textos de apoyo, mensajes legales y cierres.

Un buen microcopy reduce dudas. Explica qué pasará después de hacer clic, qué valor obtiene el usuario y por qué debería importarle.

Titulares concretos

Los titulares vagos suelen sonar elegantes, pero convierten el email en un ejercicio de interpretación. En cambio, los titulares concretos ahorran tiempo.

No es lo mismo decir:

“Tenemos novedades para ti”

que decir:

“Nueva guía gratuita para mejorar tus newsletters responsive”

El segundo titular comunica tema, formato y beneficio. La persona puede decidir más rápido si le interesa.

Botones con verbos claros

El texto del botón debería anticipar la acción. “Descargar guía”, “Leer el artículo”, “Ver ejemplos” o “Reservar sesión” son más útiles que “Más información” cuando el contexto no es evidente.

Además, el botón no debería prometer algo que la página de destino no cumple. La experiencia no termina en el email: continúa después del clic.

Reducir la carga cognitiva

Cada email obliga al usuario a tomar pequeñas decisiones: abrir o no abrir, seguir leyendo o abandonar, hacer clic o no, confiar o desconfiar. Cuantas más dudas genere el diseño, mayor será la carga cognitiva.

Por eso, un buen email responde rápido a preguntas como:

  • ¿Qué es esto?
  • ¿Por qué me interesa?
  • ¿Quién me lo envía?
  • ¿Qué tengo que hacer?
  • ¿Qué pasa si hago clic?
  • ¿Hay alguna condición importante?

La claridad no solo mejora la estética funcional del email: también reduce el esfuerzo mental. Esta idea conecta directamente con la forma en la que estructuramos cualquier interfaz. De hecho, al diseñar una newsletter conviene pensar en la misma lógica que aplicaríamos a una pantalla web: menos ruido, mejor jerarquía y decisiones más fáciles.

Estructura recomendada para una newsletter clara

No existe una única estructura válida, pero sí una lógica común que suele funcionar bien para campañas informativas, educativas o comerciales.

1. Cabecera reconocible

Incluye el logo o nombre de marca, pero sin ocupar demasiado espacio. La cabecera debe identificar al remitente, no retrasar el mensaje.

2. Titular principal

Debe explicar la idea central del correo. Aquí no conviene ser excesivamente críptica. La creatividad puede estar presente, pero sin sacrificar comprensión.

3. Beneficio o contexto

Uno o dos párrafos breves pueden explicar por qué el contenido es relevante. Este bloque debe conectar con una necesidad real del lector.

4. CTA principal

La acción principal debería aparecer pronto. Si el email es largo, se puede repetir más abajo, pero siempre manteniendo una jerarquía clara.

5. Contenido secundario

Aquí pueden entrar artículos relacionados, productos recomendados, testimonios, recordatorios o recursos adicionales. Pero deben estar visualmente subordinados al objetivo principal.

Si la newsletter forma parte de un sistema más amplio, también puede ser útil trabajar con módulos reutilizables. En ese caso, herramientas como MJML pueden ayudarte a crear una base más ordenada. Puedes ampliar esta parte en el artículo sobre qué es MJML y por qué facilita la maquetación de emails responsive.

El footer debe incluir información necesaria, enlaces de gestión de suscripción y datos legales, pero sin convertirse en un bloque caótico. También forma parte de la experiencia.

Errores frecuentes en UX de newsletters

El diseño de newsletters suele fallar no por falta de creatividad, sino por exceso de elementos sin prioridad clara.

Diseñar para impresionar, no para orientar

Una newsletter puede tener una primera impresión potente y aun así no convertir. Si el usuario piensa “qué bonito” pero no sabe qué hacer, la experiencia está incompleta.

Usar demasiadas columnas

Las columnas pueden funcionar en escritorio, pero en móvil tienden a complicarse. Si el contenido es importante, debe mantenerse claro cuando se apila.

Depender demasiado de imágenes

Una campaña construida casi por completo con imágenes puede ser visualmente atractiva, pero débil en accesibilidad, rendimiento y adaptabilidad.

Ocultar la información importante

Fechas, precios, condiciones, ubicación, duración o requisitos no deberían quedar escondidos en letra pequeña si son relevantes para la decisión.

Crear botones poco descriptivos

Un botón debe ser una señal, no un misterio. “Leer más” puede funcionar si el contexto está muy claro, pero muchas veces es mejor usar textos más específicos.

Cómo medir si tu UX de email marketing funciona

La UX también se puede evaluar. No basta con mirar aperturas o clics de forma aislada. Hay que interpretar los datos con criterio.

Una tasa de apertura puede indicar que el asunto funciona, pero no necesariamente que el contenido sea claro. Una tasa de clics baja puede deberse a un CTA poco visible, a una propuesta poco relevante o a un diseño que dispersa la atención.

Una tasa alta de bajas puede indicar problemas de frecuencia, expectativas o valor percibido. Por eso, además de revisar métricas, conviene analizar la newsletter con preguntas cualitativas.

Antes de enviar una campaña, puedes hacer esta revisión rápida:

  • ¿Se entiende el objetivo en cinco segundos?
  • ¿El CTA principal destaca sin competir con otros elementos?
  • ¿El texto se lee bien en móvil?
  • ¿El email funciona si las imágenes no cargan?
  • ¿Hay suficiente contraste?
  • ¿El orden de lectura tiene sentido?
  • ¿La promesa del asunto coincide con el contenido?

Si la respuesta a varias de estas preguntas es “no”, el problema probablemente no está en añadir más diseño, sino en simplificar la experiencia.

FAQs sobre UX en email marketing y diseño de newsletters

¿Qué es más importante en una newsletter: diseño visual o claridad?

La claridad debería ir primero. El diseño visual es importante porque transmite marca, orden y profesionalidad, pero debe estar al servicio del mensaje. Una newsletter visualmente atractiva pero difícil de entender tendrá peor experiencia de usuario que una más sencilla, clara y bien jerarquizada.

¿Cuántos CTA debería tener un email de marketing?

Lo ideal es que haya un CTA principal. Puede repetirse en distintos puntos si el email es largo, pero no debería competir con muchas acciones diferentes. Si incluyes CTAs secundarios, deben tener menor peso visual y responder a objetivos complementarios, no contradecir la acción principal.

¿Cómo puedo mejorar rápido la UX de mis newsletters?

Empieza por revisar cinco aspectos: titular principal, legibilidad del texto, contraste, visibilidad del botón principal y comportamiento en móvil. Después, comprueba si el email se entiende sin imágenes y si el orden de lectura es lógico. Con esos ajustes ya puedes mejorar bastante la experiencia sin rediseñar toda la plantilla.

Claridad, confianza y acción: la verdadera función del diseño

El UX en email marketing no consiste en quitar personalidad a las newsletters, sino en diseñarlas con más intención. La claridad no está reñida con la creatividad. De hecho, una buena idea visual se vuelve más potente cuando el mensaje se entiende sin esfuerzo.

En una bandeja de entrada saturada, la persona no le debe atención a ninguna marca. Hay que ganarla con relevancia, respeto y facilidad. Eso implica escribir mejor, jerarquizar mejor, diseñar con menos ruido y comprobar que cada decisión visual ayuda a avanzar.

La decoración puede emocionar, diferenciar y reforzar una identidad. Pero la claridad es la que permite que el usuario comprenda, confíe y actúe.

Por eso, antes de añadir otro bloque, otro icono, otro fondo o una nueva animación, merece la pena preguntarse: ¿esto mejora la experiencia o solo llena espacio?

Ahí está la diferencia entre una newsletter bonita y una newsletter realmente útil.

Por qué animar transform y opacity antes que width o height

Las animaciones pueden hacer que una interfaz resulte más clara, agradable y fácil de comprender. Un botón que responde al pasar el cursor, una tarjeta que aparece suavemente o un menú que se despliega ayudan a comunicar que se ha producido un cambio.

Sin embargo, no todas las propiedades CSS tienen el mismo coste para el navegador.

Aunque visualmente dos animaciones puedan parecer similares, internamente pueden activar procesos muy distintos. Cambiar el tamaño de un elemento mediante width o height, por ejemplo, suele requerir más trabajo que modificar su apariencia con transform. Del mismo modo, mostrar u ocultar un componente animando opacity suele ser más eficiente que alterar propiedades que afectan directamente a su geometría.

Por este motivo, una de las recomendaciones más habituales al trabajar con movimiento en interfaces web es animar transform y opacity siempre que sea posible, antes que propiedades como width, height, top o left.

Esta recomendación no es una regla arbitraria. Está relacionada con la manera en que el navegador calcula, pinta y compone cada página.

En este artículo veremos por qué conviene animar transform en CSS, cuándo es recomendable animar opacity, cómo influye la elección de propiedades en el rendimiento y qué alternativas podemos utilizar para evitar animar width y height innecesariamente.

Si todavía estás familiarizándote con estos conceptos, puedes comenzar por esta guía básica de animaciones CSS, donde explico las diferencias entre transition, animation y @keyframes.

Cómo renderiza una página el navegador

Para comprender por qué algunas animaciones son más eficientes que otras, primero debemos observar, de forma simplificada, cómo convierte el navegador nuestro HTML y CSS en los píxeles que aparecen en pantalla.

Cuando una página se carga o cambia, el navegador puede atravesar varias etapas:

  1. Cálculo de estilos.
  2. Layout o disposición.
  3. Pintado.
  4. Composición.

No todos los cambios CSS necesitan recorrer todas estas fases. Esa es precisamente la diferencia que puede hacer que una animación se perciba fluida o, por el contrario, entrecortada.

Cálculo de estilos

El navegador analiza qué reglas CSS se aplican a cada elemento.

Si añadimos una clase, modificamos un estado como :hover o cambiamos una propiedad mediante JavaScript, puede ser necesario recalcular parte de los estilos de la página.

Este proceso no siempre es especialmente costoso. El problema aparece cuando afecta a una gran cantidad de elementos o se repite continuamente durante una animación.

Por ejemplo, si una clase modifica varias propiedades en un componente complejo, el navegador debe determinar de nuevo qué estilos corresponden a cada elemento involucrado.

Layout: calcular tamaños y posiciones

Durante la fase de layout, también conocida como reflow, el navegador calcula el tamaño y la posición de los elementos dentro del documento.

Aquí intervienen propiedades como:

  • width
  • height
  • margin
  • padding
  • top
  • left
  • font-size
  • display

Cuando cambia la anchura de un elemento, también puede cambiar la posición de sus hermanos, el tamaño de su contenedor o la distribución de una sección completa.

Imagina una tarjeta situada dentro de una cuadrícula. Si modificamos su width, es posible que el navegador tenga que comprobar si las demás tarjetas caben en la misma fila, si alguna debe pasar a la siguiente línea o si el contenedor necesita cambiar de tamaño.

Por tanto, el navegador no siempre actualiza únicamente el elemento animado. En algunos casos debe volver a calcular una parte considerable de la página.

Paint: convertir los elementos en píxeles

Después del layout, el navegador pinta el contenido.

En esta fase procesa, entre otros elementos:

  • Colores.
  • Fondos.
  • Bordes.
  • Texto.
  • Imágenes.
  • Sombras.
  • Gradientes.

Propiedades como background-color, border-color o box-shadow pueden provocar nuevas operaciones de pintado.

El coste dependerá del tamaño del área modificada y de la complejidad visual del componente. No es lo mismo volver a pintar un icono pequeño que una sección que ocupa toda la pantalla y contiene sombras, imágenes y filtros.

Composición: organizar las capas

En la fase de composición, el navegador combina las distintas capas visuales y genera la imagen final que vemos en pantalla.

Propiedades como transform y opacity pueden gestionarse, en muchos casos, principalmente durante esta etapa. Esto permite reutilizar contenido que ya ha sido calculado y pintado.

Por qué la composición suele ser más eficiente

Imagina una tarjeta que ya ha sido colocada y pintada.

Si la movemos cambiando su propiedad left, el navegador puede necesitar recalcular su posición y comprobar cómo afecta el cambio al resto de la página.

En cambio, si la desplazamos utilizando transform: translateX(), el navegador puede mover visualmente una capa que ya estaba preparada.

En términos sencillos, una opción puede obligar a reconstruir parte de la escena, mientras que la otra mueve una pieza que ya existe.

Por qué conviene animar transform en CSS

La propiedad transform permite modificar visualmente un elemento sin cambiar directamente el espacio que ocupa dentro del flujo del documento.

Con ella podemos aplicar diferentes transformaciones:

  • Desplazamientos con translate().
  • Cambios de escala con scale().
  • Rotaciones con rotate().
  • Inclinaciones con skew().

Estas operaciones suelen ser adecuadas para crear animaciones porque no obligan a recolocar automáticamente los elementos que se encuentran alrededor.

Mover un elemento con left frente a translateX

Supongamos que queremos desplazar un elemento horizontalmente.

Una primera opción sería animar la propiedad left:

.elemento {
  position: relative;
  left: 0;
  transition: left 300ms ease;
}

.elemento:hover {
  left: 40px;
}

El código funciona, pero left participa en el cálculo de la posición del elemento. Durante la transición, el navegador puede tener que actualizar el layout en cada fotograma.

Una alternativa más eficiente consiste en utilizar transform:

.elemento {
  transform: translateX(0);
  transition: transform 300ms ease;
}

.elemento:hover {
  transform: translateX(40px);
}

El efecto visual es parecido, pero el segundo ejemplo puede resolverse principalmente durante la composición.

Cuando el objetivo sea crear un desplazamiento puramente visual, suele ser preferible utilizar translate() en lugar de animar top, right, bottom o left.

Cambiar el tamaño con scale frente a width

También podemos utilizar transform para simular un cambio de tamaño.

Por ejemplo, podríamos hacer crecer un botón modificando su anchura:

.boton {
  width: 180px;
  transition: width 250ms ease;
}

.boton:hover {
  width: 200px;
}

Esta transición altera el tamaño real del botón. Como consecuencia, puede afectar al texto, al contenedor y a los elementos cercanos.

En muchos casos podemos conseguir una respuesta visual similar utilizando scale():

.boton {
  transform: scale(1);
  transition: transform 250ms ease;
}

.boton:hover {
  transform: scale(1.05);
}

Ahora el espacio utilizado por el layout permanece igual. Lo que cambia es la representación visual del botón.

Este recurso puede resultar especialmente útil en botones, tarjetas o pequeños elementos gráficos. También puede aplicarse a algunos iconos creados únicamente con CSS para añadir una respuesta visual sin modificar su tamaño estructural.

Cuándo scale no sustituye realmente a width o height

Es importante comprender que scale() no modifica el espacio reservado en el documento.

Si un elemento mide 200 píxeles de ancho y aplicamos:

transform: scaleX(1.5);

visualmente será más ancho, pero el navegador continuará reservando los 200 píxeles originales dentro del layout.

Esto puede provocar que el elemento transformado se superponga con otros componentes.

Por tanto, scale() es especialmente útil para:

  • Efectos de interacción.
  • Botones que crecen ligeramente.
  • Tarjetas que destacan al pasar el cursor.
  • Iconos que cambian de tamaño.
  • Elementos que entran o salen de escena.
  • Animaciones decorativas.

No siempre es adecuado para cambios estructurales en los que el contenido debe empujar, reducir o recolocar otros elementos.

Por qué animar opacity en CSS suele ser eficiente

La propiedad opacity controla la transparencia de un elemento.

Su valor puede ir desde 0, completamente transparente, hasta 1, completamente visible:

.elemento {
  opacity: 0;
}

Una transición sencilla de aparición podría escribirse así:

.elemento {
  opacity: 0;
  transition: opacity 300ms ease;
}

.elemento.visible {
  opacity: 1;
}

Este cambio no modifica el tamaño ni la posición del componente. Por tanto, generalmente no obliga al navegador a recalcular el layout.

El navegador puede reutilizar la capa del elemento y cambiar su nivel de transparencia durante la composición.

Combinar transform y opacity

Una de las técnicas más útiles para crear entradas suaves consiste en combinar un pequeño desplazamiento con un cambio de opacidad:

.tarjeta {
  opacity: 0;
  transform: translateY(16px);
  transition:
    opacity 300ms ease,
    transform 300ms ease;
}

.tarjeta.visible {
  opacity: 1;
  transform: translateY(0);
}

En este ejemplo, la tarjeta:

  • Comienza ligeramente desplazada.
  • Aparece de forma progresiva.
  • Recupera su posición visual.
  • No necesita animar su altura ni su posición mediante top.

Esta combinación es habitual en tarjetas, modales, menús, avisos y elementos que aparecen al hacer scroll.

Cuando la animación requiere secuencias más complejas, coordinación entre varios elementos o un control preciso de los tiempos, puede ser conveniente utilizar una herramienta específica. En ese caso, puedes consultar cómo crear animaciones para la web con la librería GSAP.

Opacity no elimina el elemento del documento

Un detalle importante es que opacity: 0 no equivale a eliminar un elemento.

Un componente transparente continúa:

  • Ocupando espacio.
  • Pudiendo recibir eventos del puntero.
  • Pudiendo recibir el foco mediante el teclado.
  • Formando parte del árbol de accesibilidad si no se gestiona de otra manera.

Por eso, para ocultar correctamente un elemento interactivo puede ser necesario combinar varias propiedades:

.menu {
  opacity: 0;
  visibility: hidden;
  pointer-events: none;
  transform: translateY(-8px);
  transition:
    opacity 200ms ease,
    transform 200ms ease,
    visibility 0s linear 200ms;
}

.menu.abierto {
  opacity: 1;
  visibility: visible;
  pointer-events: auto;
  transform: translateY(0);
  transition-delay: 0s;
}

La opacidad controla la transición visual, mientras que visibility y pointer-events evitan interacciones accidentales cuando el menú está oculto.

Dependiendo del componente, también puede ser necesario actualizar atributos como aria-hidden, aria-expanded o el estado de los elementos que pueden recibir el foco.

Qué ocurre al animar width o height

Las propiedades width y height forman parte de la geometría del elemento.

Cuando cambian, el navegador puede tener que calcular de nuevo:

  • El tamaño del propio elemento.
  • La distribución de sus contenidos.
  • La posición de los elementos cercanos.
  • Las dimensiones del contenedor.
  • Los saltos de línea del texto.
  • El espacio ocupado por la sección.

Si este cálculo se repite muchas veces por segundo, la animación puede exigir más trabajo al hilo principal.

Esto no significa que animar width o height esté siempre mal. Significa que conviene comprobar si el mismo efecto puede conseguirse sin modificar continuamente el layout.

Ejemplo de una animación de width

Observemos una barra de progreso:

.barra {
  width: 0;
  height: 8px;
  transition: width 500ms ease;
}

.barra.completa {
  width: 100%;
}

Animar width puede parecer la solución más evidente. Sin embargo, podemos construir la barra con su tamaño final y animar únicamente su escala horizontal:

.barra {
  width: 100%;
  height: 8px;
  transform: scaleX(0);
  transform-origin: left;
  transition: transform 500ms ease;
}

.barra.completa {
  transform: scaleX(1);
}

El resultado visual es una barra que crece desde la izquierda, pero sin modificar su anchura real en cada fotograma.

La propiedad transform-origin es fundamental:

transform-origin: left;

Sin ella, la barra crecería desde el centro, ya que ese es el origen predeterminado de la transformación.

Ejemplo de una animación de height

Un patrón frecuente consiste en intentar desplegar un contenido animando su altura:

.contenido {
  height: 0;
  overflow: hidden;
  transition: height 300ms ease;
}

.contenido.abierto {
  height: 300px;
}

El problema es que el contenido puede no medir exactamente 300 píxeles. Además, la altura se recalcula durante toda la transición.

Otra aproximación conocida utiliza max-height:

.contenido {
  max-height: 0;
  overflow: hidden;
  transition: max-height 300ms ease;
}

.contenido.abierto {
  max-height: 600px;
}

Esta técnica puede resultar útil, pero tiene limitaciones. La duración visual real depende de la relación entre la altura del contenido y el valor máximo definido.

Si el bloque mide 150 píxeles y animamos hasta 600, el contenido llegará a su altura visible antes de que termine la transición matemática.

Alternativas para desplegar contenido

No existe una única solución válida para todos los acordeones o paneles.

Dependiendo del diseño, podemos utilizar:

  • CSS Grid.
  • JavaScript para medir scrollHeight.
  • View Transitions cuando el contexto lo permita.
  • Una combinación de opacity y transform.
  • Una animación de altura cuando sea realmente necesaria.

Un ejemplo con CSS Grid consiste en pasar de una fila con fracción cero a una fila con una fracción:

.acordeon__contenedor {
  display: grid;
  grid-template-rows: 0fr;
  transition: grid-template-rows 300ms ease;
}

.acordeon__contenedor.abierto {
  grid-template-rows: 1fr;
}

.acordeon__contenido {
  overflow: hidden;
}

Esta técnica permite desplegar contenido de altura variable sin establecer un número fijo. Aun así, sigue existiendo un cambio de layout, por lo que debe utilizarse de manera razonable.

Transform y opacity no son propiedades mágicas

Aunque el rendimiento de transform y opacity suele ser mejor, no significa que cualquier animación basada en estas propiedades vaya a funcionar perfectamente.

El coste final depende de varios factores:

  • El tamaño del elemento.
  • La cantidad de elementos animados.
  • La complejidad del contenido.
  • El dispositivo utilizado.
  • La memoria gráfica disponible.
  • La duración de la animación.
  • La presencia de filtros, sombras o desenfoques.
  • La cantidad de capas creadas.

Una animación de transform aplicada a cientos de elementos simultáneos puede seguir provocando problemas.

Del mismo modo, animar la opacidad de una capa que cubre toda la pantalla y contiene efectos complejos puede resultar más costoso de lo esperado.

Cuidado con will-change

La propiedad will-change permite avisar al navegador de que una propiedad probablemente cambiará:

.elemento {
  will-change: transform;
}

Este aviso puede ayudar al navegador a preparar determinadas optimizaciones antes de que comience la animación.

Sin embargo, no conviene aplicarlo de forma general:

* {
  will-change: transform;
}

Este enfoque puede aumentar innecesariamente el consumo de memoria y crear demasiadas capas.

Lo recomendable es utilizar will-change únicamente en componentes concretos que realmente lo necesiten:

.modal {
  will-change: transform, opacity;
}

Incluso en esos casos, debemos comprobar si aporta una mejora real. Los navegadores actuales ya realizan muchas optimizaciones sin que tengamos que indicarlas manualmente.

Cómo evitar animar width y height en casos habituales

Antes de crear una transición, conviene preguntarse qué efecto visual queremos conseguir y si realmente necesitamos modificar la estructura del documento.

En muchos casos podemos sustituir una propiedad geométrica por una transformación.

Para mover un elemento

En lugar de modificar su posición con:

left: 20px;
top: 10px;

podemos utilizar:

transform: translate(20px, 10px);

Para agrandar o reducir

En lugar de animar:

width: 110%;
height: 110%;

podemos utilizar:

transform: scale(1.1);

Para mostrar una barra de progreso

En lugar de comenzar con:

width: 0;

podemos utilizar:

transform: scaleX(0);
transform-origin: left;

Para hacer aparecer un componente

Podemos combinar:

opacity: 0;
transform: translateY(12px);

con:

opacity: 1;
transform: translateY(0);

Para ocultar contenido interactivo

Podemos combinar las siguientes propiedades:

opacity
visibility
pointer-events
transform

Cada una cumple una función diferente: transición visual, visibilidad, interacción con el puntero y movimiento.

Cuándo sí tiene sentido animar width o height

Evitar width y height no significa prohibirlas.

Hay situaciones en las que el cambio de tamaño real forma parte de la experiencia y debe modificar el layout.

Por ejemplo:

  • Un panel lateral que reduce el espacio disponible del contenido principal.
  • Un editor con columnas redimensionables.
  • Un acordeón que desplaza los elementos situados debajo.
  • Un componente que expande su contenido de forma estructural.
  • Una interfaz en la que el tamaño final no puede simularse mediante scale().

En estos casos, animar la geometría puede ser una decisión válida.

La clave está en hacerlo conscientemente, limitar el número de elementos afectados y comprobar el resultado en dispositivos reales.

La diferencia entre una animación visual y una estructural

Una animación visual modifica cómo percibimos un elemento, pero no necesita alterar el flujo de la página.

Una animación estructural cambia realmente la distribución del contenido.

Para una respuesta al pasar el cursor, un pequeño desplazamiento o una aparición, transform y opacity suelen ser suficientes.

Para un panel que debe empujar otro contenido, es posible que necesitemos cambiar el layout.

No se trata de escoger siempre la propiedad teóricamente más rápida, sino de utilizar la propiedad adecuada para el comportamiento que estamos diseñando.

Cómo comprobar el rendimiento de una animación

No es recomendable asumir que una animación funciona bien únicamente porque se ve fluida en nuestro ordenador.

Un equipo potente puede ocultar problemas que aparecerán en:

  • Teléfonos antiguos.
  • Dispositivos con poca memoria.
  • Páginas con mucho contenido.
  • Navegadores con implementaciones diferentes.
  • Situaciones en las que se ejecutan varios procesos simultáneamente.

Las herramientas de desarrollo del navegador permiten analizar el trabajo realizado durante una animación.

Podemos revisar:

  • La actividad del hilo principal.
  • Los cálculos de estilo.
  • Las operaciones de layout.
  • Las tareas de pintado.
  • Los fotogramas lentos.
  • La creación de capas.
  • Las zonas que se vuelven a pintar.

Si al animar un componente aparecen operaciones de layout continuas, puede ser una señal de que estamos utilizando propiedades geométricas innecesariamente.

También conviene evaluar la animación limitando artificialmente la CPU desde las herramientas de desarrollo y comprobarla en un dispositivo móvil real.

Accesibilidad y prefers-reduced-motion

El rendimiento no es el único criterio que debemos considerar.

Algunas personas pueden experimentar molestias, mareos o dificultades de concentración ante movimientos intensos. Por eso, es importante respetar la preferencia prefers-reduced-motion.

Podemos establecer una animación normal y reducirla cuando la persona haya solicitado menos movimiento en su sistema:

.tarjeta {
  opacity: 0;
  transform: translateY(16px);
  transition:
    opacity 300ms ease,
    transform 300ms ease;
}

.tarjeta.visible {
  opacity: 1;
  transform: translateY(0);
}

@media (prefers-reduced-motion: reduce) {
  .tarjeta {
    transform: none;
    transition-duration: 1ms;
  }
}

En algunos componentes puede ser mejor eliminar la transición por completo:

@media (prefers-reduced-motion: reduce) {
  .elemento-animado {
    animation: none;
    transition: none;
  }
}

Reducir el movimiento no significa ocultar información. El componente debe seguir siendo comprensible y funcional aunque la animación desaparezca.

Buenas prácticas para crear animaciones CSS eficientes

Una animación efectiva no depende únicamente de las propiedades utilizadas. También influyen su duración, su propósito y el contexto en el que aparece.

Animar solo lo necesario

Evita añadir movimiento a todos los elementos de la interfaz.

Cada animación debería cumplir alguna función:

  • Confirmar una acción.
  • Mostrar una relación entre estados.
  • Orientar la atención.
  • Explicar la aparición de un componente.
  • Suavizar un cambio.
  • Comunicar progreso.

Cuando todo se mueve, ningún movimiento destaca.

Mantener duraciones razonables

Las microinteracciones suelen funcionar bien con duraciones breves, aunque no existe un valor universal.

Una transición demasiado lenta puede hacer que la interfaz parezca pesada. Una transición excesivamente rápida puede resultar imperceptible o brusca.

Como referencia inicial, muchos efectos pequeños pueden situarse entre 150 y 300 milisegundos. No obstante, el valor debe ajustarse según la distancia recorrida, el tamaño del elemento y la importancia del cambio.

Evitar transition: all

Es frecuente encontrar reglas como esta:

.elemento {
  transition: all 300ms ease;
}

Aunque resulte cómoda, puede animar propiedades que no teníamos intención de modificar.

Es mejor especificar qué propiedades deben cambiar:

.elemento {
  transition:
    transform 300ms ease,
    opacity 300ms ease;
}

De esta forma, el comportamiento es más predecible y reducimos el riesgo de crear transiciones costosas accidentalmente.

Utilizar transform-origin correctamente

Cuando trabajamos con scale() o rotate(), el punto de origen cambia la percepción del movimiento.

Por ejemplo:

transform-origin: left center;

puede hacer que un indicador crezca desde la izquierda, mientras que:

transform-origin: center;

hará que se expanda en ambas direcciones.

Elegir el origen adecuado permite sustituir muchas animaciones de anchura o altura por transformaciones visualmente coherentes.

No olvidar las animaciones SVG

Los mismos criterios de rendimiento pueden aplicarse a gráficos e ilustraciones.

En lugar de reconstruir continuamente el tamaño o la geometría de un elemento, podemos animar desplazamientos, rotaciones y opacidad. Para profundizar en este tipo de recursos, puedes consultar el artículo sobre Sass y animaciones SVG.

Errores frecuentes al optimizar animaciones

Uno de los errores más habituales es sustituir todas las propiedades por transform sin considerar el comportamiento real del layout.

Otro consiste en aplicar will-change a numerosos componentes con la idea de que mejorará automáticamente el rendimiento.

También debemos evitar:

  • Animar decenas de elementos sin comprobar el coste.
  • Utilizar filtros intensivos junto con grandes desplazamientos.
  • Ejecutar animaciones infinitas que no aportan información.
  • Mantener elementos transparentes pero interactivos.
  • Ignorar prefers-reduced-motion.
  • Evaluar el rendimiento únicamente en un ordenador potente.
  • Utilizar transition: all por comodidad.
  • Crear animaciones largas para acciones frecuentes.
  • Usar scale() cuando el elemento debe modificar realmente el layout.

La optimización no consiste en memorizar una lista de propiedades permitidas y prohibidas. Consiste en comprender qué trabajo estamos pidiendo al navegador.

Preguntas frecuentes sobre transform, opacity, width y height

¿Por qué transform suele rendir mejor que width o height?

transform modifica principalmente la representación visual del elemento y, en muchos casos, puede gestionarse durante la fase de composición.

Por el contrario, width y height cambian la geometría real del componente y pueden obligar al navegador a recalcular el layout, recolocar otros elementos y volver a pintar parte de la página.

¿Siempre debo evitar animar width y height?

No. Debes evitarlas cuando el efecto sea puramente visual y pueda resolverse con transform.

Si el cambio debe modificar realmente el espacio disponible, desplazar otros componentes o reorganizar el contenido, animar width o height puede ser necesario. Lo importante es utilizar estas propiedades de forma controlada y comprobar su impacto.

¿Es suficiente usar transform y opacity para garantizar una animación fluida?

No. Estas propiedades suelen ser más eficientes, pero el resultado depende del tamaño de los elementos, la cantidad de animaciones, los efectos visuales utilizados, el dispositivo y la complejidad de la página.

Una animación con transform también puede funcionar mal si afecta a demasiados elementos, utiliza capas muy grandes o se combina con filtros y sombras complejas.

Elegir bien qué animar también es diseñar mejor

Elegir entre transform, opacity, width o height no es únicamente una decisión técnica. También es una decisión de diseño.

Cuando animamos una propiedad geométrica, estamos pidiendo al navegador que vuelva a calcular cómo encajan las piezas de la interfaz. Cuando utilizamos transform u opacity, normalmente modificamos cómo se presenta una pieza que ya ha sido calculada.

Por eso, animar transform y opacity suele ofrecer una experiencia más fluida que animar width o height. Sin embargo, esta recomendación no debería convertirse en una regla rígida.

Antes de implementar cualquier movimiento, conviene plantearse una pregunta:

¿Este elemento necesita cambiar realmente el layout o solo debe parecer que se mueve, crece o aparece?

Si el cambio es visual, transform y opacity probablemente sean el mejor punto de partida. Si el cambio es estructural, quizá necesitemos modificar la geometría real.

Una buena animación no es la que utiliza más efectos ni la que resulta más espectacular. Es aquella que ayuda a comprender la interfaz, responde con fluidez y respeta tanto el rendimiento del dispositivo como las preferencias de la persona usuaria.