En esta página

Responsive design

12 min lectura TextoCap. 3 — Layout moderno

Qué es responsive design?

Responsive design es la estrategia de construir sitios web que se adaptan a cualquier tamaño de pantalla: desde telefonos de 320px hasta monitores de 4K. En lugar de crear versiones separadas, un solo sitio se ajusta fluidamente.

Los tres pilares del responsive design son:

  1. Viewport meta tag (imprescindible)
  2. Media queries (puntos de quiebre)
  3. Unidades y funciones fluidas (clamp, vw, %)

La meta etiqueta viewport

Sin esta etiqueta, los navegadores móviles renderizan la página como si fuera un escritorio y la encogen. Es obligatoria:

<meta name="viewport" content="width=device-width, initial-scale=1">

Mobile first

La estrategia mobile first consiste en escribir los estilos base para pantallas pequenas y usar media queries para agregar complejidad en pantallas grandes.

/* Base: móvil (una columna) */
.grid { display: grid; grid-template-columns: 1fr; }

/* Tablet: dos columnas */
@media (width >= 768px) {
  .grid { grid-template-columns: repeat(2, 1fr); }
}

/* Desktop: tres columnas */
@media (width >= 1024px) {
  .grid { grid-template-columns: repeat(3, 1fr); }
}

Es más fácil agregar complejidad para pantallas grandes que quitar complejidad para pantallas pequenas.

Media queries modernas

La sintaxis moderna usa operadores de comparación en lugar de min-width y max-width:

/* Sintaxis clásica */
@media (min-width: 768px) { }

/* Sintaxis moderna (recomendada) */
@media (width >= 768px) { }

/* Rango */
@media (768px <= width < 1024px) { }

Breakpoints recomendados

Nombre Ancho Uso tipico
sm 640px Telefonos grandes
md 768px Tablets
lg 1024px Laptops
xl 1280px Escritorios
2xl 1536px Pantallas grandes

No es obligatorio usar todos. Usa solo los que necesites para tu contenido.

Unidades fluidas

Porcentajes y unidades de viewport

Unidad Relativa a
% Elemento padre
vw 1% del ancho del viewport
vh 1% del alto del viewport
dvh Alto dinámico (respeta barra de dirección móvil)
svh Alto más pequeño posible
lvh Alto más grande posible

La función clamp()

clamp(mínimo, ideal, máximo) es la herramienta más poderosa para valores fluidos:

/* Tipografia que escala con la pantalla */
h1 { font-size: clamp(1.5rem, 4vw, 3.5rem); }

/* Ancho de contenido legible */
.contenido { max-width: clamp(45ch, 80%, 75ch); }

/* Padding que se adapta */
.sección { padding: clamp(1rem, 5vw, 4rem); }

Con clamp() puedes eliminar muchos media queries.

Imagenes responsivas

Las imagenes deben adaptarse a su contenedor sin desbordarse:

img {
  max-width: 100%;
  height: auto;
  display: block;
}

Para más control, usa el atributo HTML srcset con diferentes resoluciones:

<img
  src="foto-800.jpg"
  srcset="foto-400.jpg 400w, foto-800.jpg 800w, foto-1200.jpg 1200w"
  sizes="(width >= 1024px) 33vw, (width >= 768px) 50vw, 100vw"
  alt="Descripcion de la foto"
>

Container queries

Los media queries responden al tamaño del viewport. Los container queries responden al tamaño del contenedor padre. Esto hace que los componentes sean verdaderamente reutilizables.

.wrapper {
  container-type: inline-size;
}

@container (width >= 400px) {
  .card {
    display: flex;
    gap: 1rem;
  }
}

Con container queries, un componente card se adapta segun donde lo coloques: en un sidebar estrecho se ve vertical, en un area amplia se ve horizontal. Sin cambiar nada en el componente.

Layouts responsivos sin media queries

Combinando las herramientas de Grid y Flexbox, puedes crear layouts que se adaptan automaticamente:

/* Auto-fill + minmax = columnas automaticas */
.grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
  gap: 1rem;
}

/* Flexbox wrap con basis mínimo */
.cards {
  display: flex;
  flex-wrap: wrap;
  gap: 1rem;
}
.card { flex: 1 1 300px; }

Tu sitio ya se adapta a cualquier pantalla. Ahora vamos a perfeccionar la tipografia, un elemento crucial para la legibilidad y la estetica.

Práctica

  1. Implementa un layout mobile first: Crea una cuadricula de articulos que muestre 1 columna en movil, 2 en tablet (768px) y 3 en desktop (1024px) usando media queries con la sintaxis moderna (width >= ...).
  2. Usa clamp() para tipografia fluida: Aplica font-size: clamp(...) a un titulo y un parrafo para que escalen suavemente entre pantallas pequenas y grandes sin media queries.
  3. Crea un componente con container queries: Envuelve una tarjeta en un contenedor con container-type: inline-size y usa @container para cambiar su layout segun el ancho del contenedor.
Mobile first
Siempre escribe los estilos base para móvil y agrega complejidad con @media (width >= ...) para pantallas más grandes. Es más fácil agregar complejidad que quitarla.
No olvides el viewport
Sin la meta etiqueta viewport en tu HTML, los media queries no funcionaran correctamente en dispositivos móviles. Asegurate de incluir <meta name="viewport" content="width=device-width, initial-scale=1">.
/* Mobile first: estilos base para móvil */
.grid-articulos {
  display: grid;
  grid-template-columns: 1fr;
  gap: 1.5rem;
  padding: 1rem;
}

/* Tablet: 2 columnas */
@media (width >= 768px) {
  .grid-articulos {
    grid-template-columns: repeat(2, 1fr);
    padding: 2rem;
  }
}

/* Desktop: 3 columnas con sidebar */
@media (width >= 1024px) {
  .layout {
    display: grid;
    grid-template-columns: 1fr 300px;
    gap: 2rem;
  }

  .grid-articulos {
    grid-template-columns: repeat(2, 1fr);
  }
}

/* Tipografia fluida con clamp() */
.título {
  font-size: clamp(1.5rem, 4vw, 3rem);
  line-height: 1.2;
}

.contenido {
  max-width: clamp(45ch, 60%, 75ch);
  margin-inline: auto;
}
/* Container queries: responder al contenedor, no al viewport */
.card-wrapper {
  container-type: inline-size;
  container-name: card;
}

.card {
  display: grid;
  grid-template-columns: 1fr;
  gap: 1rem;
  padding: 1rem;
}

/* Cuando el CONTENEDOR tiene 400px+ */
@container card (width >= 400px) {
  .card {
    grid-template-columns: 150px 1fr;
    align-items: center;
  }
}

@container card (width >= 600px) {
  .card {
    grid-template-columns: 200px 1fr auto;
  }
}