CSS y web

Degradados SVG: lineales, radiales, trazos, texto y máscaras

SVG tiene su propio sistema de degradados, más antiguo que los de CSS y capaz de cosas que estos no pueden: colorear un trazo, rellenar una palabra, compartir un degradado entre muchas formas y fundir cualquier cosa con una máscara.

GradientlyCuenta verificada de Gradiently··6 min de lectura
Portada: Cold Salon · GR·4AB2·SW

La versión corta

  • Un degradado SVG se define una vez como un elemento linearGradient o radialGradient con hijos stop, se le da un id y se aplica con fill o stroke igual a url(#id).
  • Por defecto, las coordenadas de un degradado SVG usan unidades objectBoundingBox, en las que 0 y 1 son los bordes de la forma que se pinta.
  • gradientUnits="userSpaceOnUse" coloca el degradado en las coordenadas propias del dibujo, lo que permite que un degradado abarque varias formas y soluciona los degradados en líneas perfectamente rectas.
  • spreadMethod decide qué pasa más allá de los extremos del degradado: pad mantiene los colores finales, reflect refleja la mezcla y repeat la vuelve a empezar.
  • Una máscara SVG usa la luminosidad, así que un degradado de blanco a negro dentro de una máscara funde aquello a lo que se aplica.
En esta página

Un degradado SVG es una pintura que defines una vez y aplicas a cualquier forma, línea o texto de un SVG. Escribes un elemento <linearGradient> o <radialGradient> dentro de <defs>, le das hijos <stop> para sus colores y un id, y luego pones el fill o el stroke de una forma a url(#id). A diferencia de un fondo CSS, puede colorear un trazo o una sola palabra, y escala con el dibujo.

html
<svg viewBox="0 0 200 120" xmlns="http://www.w3.org/2000/svg">
  <defs>
    <linearGradient id="dusk" x1="0" y1="0" x2="1" y2="1">
      <stop offset="0" stop-color="#1e1b4b" />
      <stop offset="0.55" stop-color="#7c3aed" />
      <stop offset="1" stop-color="#f472b6" />
    </linearGradient>
  </defs>
  <rect width="200" height="120" rx="16" fill="url(#dusk)" />
</svg>
Un degradado diagonal en un rectángulo redondeado. x1, y1, x2 e y2 trazan la línea del degradado de arriba a la izquierda a abajo a la derecha.
La misma mezcla, en CSSlinear-gradient(135deg, #1e1b4b 0%, #7c3aed 55%, #f472b6 100%)
El SVG de arriba y este degradado CSS coinciden en un cuadrado. En un rectángulo, la versión SVG se estira con la forma; mira gradientUnits más abajo.

linearGradient y sus paradas

x1, y1, x2 e y2 fijan el inicio y el final de la línea del degradado. Cada <stop> lleva un offset de 0 a 1 (o de 0% a 100%), un stop-color y un stop-opacity opcional. stop-color también es una propiedad CSS, así que puedes cambiar el tema de los degradados desde una hoja de estilos, por ejemplo stop { stop-color: var(--accent); }.

AtributoPor defectoQué hace
x1 y1 x2 y20 0 1 0, de izquierda a derechaPuntos de inicio y final de la línea del degradado
gradientUnitsobjectBoundingBoxSi las coordenadas son relativas a la forma o al dibujo
spreadMethodpadQué pasa más allá de los extremos: pad, reflect o repeat
gradientTransformningunoGira, escala o inclina el degradado, p. ej. rotate(30)
hrefningunoHereda las paradas y los ajustes de otro degradado
Los atributos principales de linearGradient. radialGradient comparte todos menos la primera fila.

href ahorra repeticiones. Define tus paradas una vez en un degradado base y luego crea variaciones que apunten a él y cambien solo la dirección o las unidades. La referencia de linearGradient en MDN cubre todos los atributos.

radialGradient: centro, radio y punto focal

Un degradado radial toma un centro (cx, cy) y un radio (r), todos con 0,5 por defecto, así que rellena la forma desde el centro. También tiene algo que a CSS le falta: un punto focal independiente (fx, fy) donde empieza el primer color. Mover el punto focal fuera del centro hace que una esfera parezca iluminada desde un lado.

html
<radialGradient id="orb" cx="0.5" cy="0.5" r="0.5" fx="0.32" fy="0.28">
  <stop offset="0" stop-color="#e0f2fe" />
  <stop offset="0.45" stop-color="#0ea5e9" />
  <stop offset="1" stop-color="#082f49" />
</radialGradient>

<circle cx="60" cy="60" r="50" fill="url(#orb)" />
Un punto focal arriba a la izquierda convierte un círculo plano en una esfera brillante.
Esfera iluminada, aproximada en CSSradial-gradient(circle at 32% 28%, #e0f2fe, #0ea5e9 35%, #082f49 80%)
CSS puede mover el centro, pero no separar centro y foco, así que esto es solo una aproximación de la esfera SVG. Compáralo con los degradados radiales en CSS.

gradientUnits: objectBoundingBox o userSpaceOnUse

Con el valor por defecto, objectBoundingBox, 0 y 1 significan los bordes de la forma que se esté pintando, así que cada forma recibe el degradado entero, estirado para encajar. Con userSpaceOnUse, las coordenadas están en las unidades propias del SVG, así que el degradado se queda en su sitio y cada forma muestra la parte que cubre. Así es como una fila de barras puede compartir un único degradado continuo.

objectBoundingBox

  • Coordenadas de 0 a 1 a lo largo de cada forma
  • Cada forma muestra el degradado completo
  • El degradado se estira con las proporciones de la forma
  • Falla en una línea perfectamente horizontal o vertical

userSpaceOnUse

  • Coordenadas en las unidades propias del dibujo
  • Cada forma muestra su trozo de un único degradado
  • Los ángulos se mantienen sea cual sea la forma
  • Funciona en líneas rectas y trazos finos

Degradados en trazos y texto

stroke="url(#id)" pinta los contornos, y así se dibujan los iconos con degradado, los anillos de progreso y las líneas de los gráficos. En <text>, fill="url(#id)" colorea las letras y las palabras siguen siendo seleccionables y buscables. Añade un color plano después de la URL, como fill="url(#dusk) #7c3aed", y se usará si no se encuentra el degradado.

html
<svg viewBox="0 0 320 120" xmlns="http://www.w3.org/2000/svg">
  <defs>
    <linearGradient id="line" gradientUnits="userSpaceOnUse" x1="20" y1="0" x2="300" y2="0">
      <stop offset="0" stop-color="#22d3ee" />
      <stop offset="1" stop-color="#a855f7" />
    </linearGradient>
  </defs>
  <path d="M20 90 C 90 20, 160 110, 300 30" fill="none" stroke="url(#line)" stroke-width="6" stroke-linecap="round" />
  <text x="20" y="115" font-size="20" font-weight="700" fill="url(#line) #7c3aed">Growth</text>
</svg>
Un degradado en unidades del dibujo, compartido por una curva y una palabra. Los dos van del cian al morado a lo largo del mismo tramo horizontal.

Para letras con degradado en HTML y no en SVG, el texto con degradado en CSS suele ser más sencillo. Recurre al texto SVG cuando las palabras formen parte de una ilustración o un logotipo, o tengan que seguir un trazado.

spreadMethod: pad, reflect y repeat

Cuando la línea del degradado es más corta que la forma, spreadMethod decide qué rellena el resto. pad mantiene los colores de los extremos, reflect refleja la mezcla de ida y vuelta y repeat la vuelve a empezar con un borde duro. Aquí cada degradado va del 30% al 70% del ancho.

Del verde azulado a la arena con los tres métodos de extensión, reproducidos en CSS para que puedas compararlos uno junto a otro.

Fundidos con máscaras SVG

Una máscara usa la luminosidad: las zonas blancas muestran lo enmascarado, las negras lo ocultan y los grises quedan a medio camino. Por eso un degradado de blanco a negro dentro de una <mask> funde cualquier forma o imagen suavemente hasta desaparecer, y así se suaviza el borde de una foto o se hace que la línea de un gráfico se desvanezca al principio.

html
<defs>
  <linearGradient id="fade" x1="0" y1="0" x2="0" y2="1">
    <stop offset="0.4" stop-color="#fff" />
    <stop offset="1" stop-color="#000" />
  </linearGradient>
  <mask id="soft-bottom">
    <rect width="100%" height="100%" fill="url(#fade)" />
  </mask>
</defs>

<image href="photo.jpg" width="100%" height="100%" mask="url(#soft-bottom)" />
La foto se ve entera arriba y se desvanece a lo largo de su 60% inferior.

En los elementos HTML, mask-image: linear-gradient(#000 40%, transparent) en CSS hace lo mismo, usando la transparencia en lugar de la luminosidad. La técnica de la máscara también sirve para los bordes con degradado en CSS transparentes.

Evita

  • Reutilizar el mismo id de degradado en dos SVG en línea de una misma página
  • Ocultar un sprite de definiciones de degradado con display: none
  • Las unidades por defecto en líneas rectas
  • Degradados oscuros muy largos y suaves sin textura

Haz

  • Ids únicos, o un único sprite de definiciones compartido
  • Oculta los sprites con ancho y alto cero
  • userSpaceOnUse para trazos y degradados compartidos
  • Añade grano a los fundidos grandes, mira textura de ruido en CSS

Preguntas frecuentes

¿Cómo añado un degradado a un SVG?

Define un <linearGradient> o <radialGradient> con hijos <stop> y un id dentro de <defs>, y luego pon el fill o el stroke de una forma a url(#id).

¿Por qué no se ve el trazo con degradado SVG en una línea?

Una línea recta horizontal o vertical tiene una caja delimitadora de tamaño cero, así que las unidades objectBoundingBox por defecto fallan. Usa gradientUnits="userSpaceOnUse" con coordenadas reales.

¿Cómo giro un degradado SVG?

Cambia x1, y1, x2 e y2, o añade gradientTransform="rotate(45 0.5 0.5)" para girarlo alrededor del centro de la caja delimitadora.

¿Puedo cambiar los colores de un degradado SVG con CSS?

Sí. stop-color y stop-opacity son propiedades CSS, así que reglas como stop { stop-color: var(--accent); } funcionan en SVG en línea.

¿Por qué desapareció mi degradado SVG al ocultar el SVG?

Las definiciones dentro de un SVG con display: none pueden no renderizarse. Oculta el sprite con ancho y alto cero, o con posicionamiento absoluto.

Compartir esta guía

Escrito por GradientlyCuenta verificada de Gradiently

El equipo detrás de Gradiently, una herramienta de diseño creada en torno a los Marks: degradados vivos que hacen que todo lo que diseñas parezca tuyo.

Ver nuestro perfil