¡Ah, las media queries! Esa vieja amiga que nos ha acompañado durante años, fiel como un reloj suizo, pero con la flexibilidad de una barra de hierro.
Durante más de una década, los desarrolladores web hemos estado haciendo malabares con breakpoints globales como si estuviéramos en el circo del responsive, intentando que nuestros componentes se vean bien en todas partes.
CSS Container Queries emerge como una solución revolucionaria que permite crear componentes completamente adaptables, capaces de responder no solo al tamaño de la ventana del navegador, sino al contexto específico donde se encuentran.
El problema del diseño responsive tradicional
El diseño web responsive tradicional, basado en Media Queries, presenta varios problemas:
- Dependencia del viewport: Los estilos se aplican basándose únicamente en el tamaño de la ventana del navegador, ignorando el contexto real donde se muestra cada componente.
- Falta de reusabilidad: Un componente diseñado para funcionar en una sección específica puede no adaptarse correctamente cuando se coloca en un contexto diferente.
- Complejidad de mantenimiento: Los breakpoints globales pueden volverse difíciles de mantener en proyectos grandes.
- Limitaciones en la composición: La creación de layouts complejos con componentes anidados se vuelve problemática cuando solo se puede responder al viewport.
Container Queries: La solución adaptativa
Las Container Queries representan un cambio de paradigma en el diseño web responsive. En lugar de basar las decisiones de diseño en el viewport, permiten que los componentes respondan al tamaño de su contenedor más cercano. Esto ofrece varias ventajas:
- Componentes reutilizables «de verdad»
- Mayor control sobre el diseño
- Mejor encapsulamiento
- Diseño más predecible
- Mantenimiento simplificado
Implementación básica de Container Queries
Creación de un contexto de contención
Para utilizar Container Queries, primero debemos establecer un contexto de contención:
CSS:
.container {
container-type: inline-size;
container-name: main-content;
}
Los valores disponibles para container-type
son:
size
: Habilita consultas en ambas dimensiones (ancho y alto)inline-size
: Permite consultas solo en la dimensión inline (generalmente el ancho)normal
: Desactiva las consultas de tamaño pero mantiene otras funcionalidades
Estructura básica de una Container Query:
CSS:
@container (min-width: 400px) {
.card {
display: grid;
grid-template-columns: 2fr 1fr;
gap: 1rem;
}
}
Aquí un ejemplo práctico completo:
HTML:
@container (min-width: 400px) {
.card {
display: grid;
grid-template-columns: 2fr 1fr;
gap: 1rem;
}
}
CSS:
.container {
container-type: inline-size;
}
.card {
display: flex;
flex-direction: column;
gap: 1rem;
padding: 1rem;
}
@container (min-width: 500px) {
.card {
flex-direction: row;
}
.card__image {
flex: 1;
}
.card__content {
flex: 2;
}
}
@container (min-width: 800px) {
.card {
padding: 2rem;
}
.card__title {
font-size: 2rem;
}
}
Contextos de contención avanzados
Contención con nombre
Los contextos de contención pueden nombrarse para mayor especificidad:
CSS:
.sidebar {
container-type: inline-size;
container-name: sidebar;
}
@container sidebar (min-width: 300px) {
.widget {
grid-template-columns: repeat(2, 1fr);
}
}
Contención anidada
Los contenedores pueden anidarse para crear diseños más complejos:
CSS:
.main-layout {
container-type: inline-size;
container-name: main;
}
.sidebar {
container-type: inline-size;
container-name: sidebar;
}
@container main (min-width: 1200px) {
.layout {
display: grid;
grid-template-columns: 3fr 1fr;
}
}
@container sidebar (min-width: 200px) {
.widget {
padding: 1rem;
}
}
Unidades de longitud en Container Queries
Las Container Queries introducen nuevas unidades de longitud que se relacionan con el tamaño del contenedor:
cqw
: 1% del ancho del contenedorcqh
: 1% del alto del contenedorcqi
: 1% del tamaño inline del contenedorcqb
: 1% del tamaño de bloque del contenedorcqmin
: El menor valor entrecqi
ycqb
cqmax
: El mayor valor entrecqi
ycqb
Ejemplo de uso 👇🏻
CSS:
.card__title {
font-size: calc(1rem + 1.5cqi);
margin-bottom: 1cqw;
}
.card__image {
max-height: 50cqh;
object-fit: cover;
}
Patrones de diseño y casos de uso
Componentes de tarjeta adaptables:
CSS:
.card-container {
container-type: inline-size;
}
.card {
display: flex;
flex-direction: column;
}
@container (min-width: 400px) {
.card {
flex-direction: row;
align-items: start;
}
.card__image {
width: 40%;
}
.card__content {
width: 60%;
padding-left: 1rem;
}
}
Navegación responsive:
CSS:
.nav-container {
container-type: inline-size;
}
.nav {
display: flex;
flex-direction: column;
}
@container (min-width: 600px) {
.nav {
flex-direction: row;
justify-content: space-between;
}
.nav__item {
margin: 0 1rem;
}
}
Consideraciones de rendimiento
Para optimizar el rendimiento al usar Container Queries:
- Minimizar el número de contextos de contención
- Crear solo los necesarios
- Evitar la contención innecesaria en elementos pequeños
- Optimizar las consultas
- Agrupar consultas similares
- Evitar rangos de consulta muy pequeños
- Gestionar el reflow
- Considerar el impacto en el layout
- Usar
content-visibility
cuando sea apropiado
Compatibilidad y estrategias de fallback
Detección de soporte:
CSS:
@supports (container-type: inline-size) {
.container {
container-type: inline-size;
}
}
@supports not (container-type: inline-size) {
/* Estilos de fallback */
}
Fallbacks progresivos:
CSS:
/* Estilo base para todos los navegadores */
.card {
display: flex;
flex-direction: column;
}
/* Media Query como fallback */
@media (min-width: 768px) {
.card {
flex-direction: row;
}
}
/* Container Query para navegadores modernos */
@supports (container-type: inline-size) {
.card-container {
container-type: inline-size;
}
@container (min-width: 400px) {
.card {
flex-direction: row;
}
}
}
Mejores prácticas y recomendaciones
- Planificación de componentes
- Identificar componentes que necesitan adaptarse
- Establecer jerarquías claras de contención
- Organización del código
- Mantener las consultas cerca de los componentes relacionados
- Usar nombres descriptivos para los contenedores
- Debugging
- Utilizar DevTools para inspeccionar contenedores
- Implementar indicadores visuales durante el desarrollo
- Optimización
- Minimizar la profundidad de anidación
- Reutilizar valores comunes mediante variables CSS
Cómo serán las Container Queries en el futuro
Las Container Queries continúan evolucionando con nuevas características en desarrollo:
- Container Style Queries: Consultas basadas en estilos del contenedor
- Consultas anidadas: Mayor flexibilidad en la composición
- Nuevas unidades y funciones: Más opciones para cálculos relativos
- Integración con Grid y Flexbox: Mejoras en la disposición adaptativa
Ejemplo de uso futuro 👇🏻
CSS:
@container style(--theme: dark) {
.component {
background: var(--dark-bg);
color: var(--dark-text);
}
}
@container grid(min-tracks: 3) {
.grid-item {
aspect-ratio: 16/9;
}
}
Si has pasado años en el desarrollo web, probablemente tengas ese tic nervioso cada vez que escuchas «necesitamos que este componente se vea diferente en el sidebar«. Esos momentos en los que mirabas al cielo preguntándote por qué las media queries solo podían ver el viewport, como si el mundo fuera un móvil tamaño planeta.
Recordemos con «cariño» esas inolvidables sesiones de depuración:
- Las infinitas media queries que hacían que tu archivo CSS pareciera la saga completa de El Señor de los Anillos
- Esos momentos zen calculando breakpoints como si fueras un monje budista de las matemáticas
- Las explicaciones a clientes sobre por qué su widget se veía perfecto en la página principal pero parecía haber sido diseñado por un gato en el sidebar
- Los momentos «¡Olé!» que terminaban en «Oh, fu*k» cuando tu solución funcionaba en todos lados excepto en esa única página que nadie recordaba que existía.
Así que la próxima vez que alguien te pida un componente que «funcione en todas partes», podrás sonreír sabiendo que tienes Container Queries en tu arsenal.
No hay comentarios on Las CSS Container Queries revolucionan el diseño web responsive