interpolate-size y calc-size(), con el soporte real
Cómo se activan, qué desbloquean exactamente, en qué motores están en 2026 y cómo escribirlas de forma que su ausencia no rompa nada.
La solución al problema de auto llegó en dos piezas complementarias: una propiedad que habilita la interpolación de las palabras clave de tamaño intrínseco, y una función que permite hacer aritmética con el valor que esas palabras resuelven. Las dos son elegantes, las dos hacen exactamente lo que prometen, y las dos tienen en agosto de 2026 una limitación que hay que decir antes que nada: solo están implementadas en Chromium. Esta lección las enseña completas y después explica cómo escribirlas para que su ausencia sea invisible.
- Activar
interpolate-sizey entender por qué se hereda. - Escribir
calc-size()con sus dos argumentos y usar la palabra clavesize. - Enunciar el estado de soporte de ambas en 2026 sin exagerarlo.
- Escribir el patrón de mejora progresiva que degrada sin romper.
interpolate-size
Es una propiedad con dos valores: numeric-only, que es el inicial y reproduce el comportamiento de siempre, y allow-keywords, que habilita la interpolación entre longitudes y palabras clave de tamaño intrínseco.
Es heredada, lo que es una decisión de diseño deliberada: permite activarla una vez en la raíz y que afecte a todo el documento, en lugar de tener que ponerla en cada componente.
:root {
interpolate-size: allow-keywords;
}
.panel {
height: 0;
overflow: hidden;
transition: height 300ms cubic-bezier(0.2, 0, 0, 1);
}
.panel[data-abierto] {
height: auto; /* ahora interpola */
}
Eso es todo. Sin envoltorios, sin medición, sin JavaScript. Y funciona igual con las demás palabras clave: min-content, max-content, fit-content y stretch, en todas las propiedades de dimensionado.
Un detalle que hay que tener claro: la interpolación se hace sobre el valor resuelto en cada fotograma. Es decir, si el contenido cambia de tamaño a mitad de la animación, la animación se adapta. Eso resuelve el segundo de los problemas técnicos que vimos en la lección anterior y es lo que la distingue de cualquier técnica basada en medir un número al empezar.
calc-size()
interpolate-size habilita las palabras clave desnudas. calc-size() va un paso más allá: permite operar con el valor que la palabra clave resuelve.
Su sintaxis tiene dos argumentos. El primero es la base: la palabra clave cuyo valor quieres resolver. El segundo es una expresión donde la palabra size representa ese valor resuelto.
/* El tamano intrinseco tal cual. Equivale a auto, pero explicito. */
height: calc-size(auto, size);
/* La mitad del tamano intrinseco. */
height: calc-size(auto, size / 2);
/* El tamano intrinseco mas dos rem de holgura. */
height: calc-size(max-content, size + 2rem);
/* Acotado: nunca mas de 20rem. */
height: calc-size(auto, min(size, 20rem));
Y aquí hay algo importante que se suele pasar por alto: calc-size() produce un valor interpolable por sí sola, sin necesidad de interpolate-size. La propiedad habilita la palabra clave desnuda; la función es una activación explícita por valor. Eso da dos formas de escribir lo mismo, y la segunda es más localizada:
/* Forma A: activacion global, palabra clave desnuda. */
:root { interpolate-size: allow-keywords; }
.panel[data-abierto] { height: auto; }
/* Forma B: sin activacion global, valor explicito. */
.panel[data-abierto] { height: calc-size(auto, size); }
La forma B tiene una ventaja en bases de código grandes: no cambia el comportamiento de nada que no hayas tocado. La forma A es más cómoda cuando controlas todo el documento.
calc-size() acepta como base cualquiera de las palabras clave de tamaño intrínseco, y también any, que significa “sea cual sea el valor de la otra parte de la interpolación”. Se puede anidar, aunque rara vez hace falta.
El soporte real, sin adornos
En agosto de 2026 la situación es esta:
| Motor | interpolate-size |
calc-size() |
|---|---|---|
| Chrome y Edge | Desde la versión 129, septiembre de 2024 | Desde la versión 129 |
| Firefox | No implementado | No implementado |
| Safari | No implementado | No implementado |
No es Baseline, ni newly ni widely. Es una capacidad de disponibilidad limitada, presente en un solo motor desde hace casi dos años. Hay solicitudes abiertas en los otros dos y es razonable esperar que llegue, pero a día de hoy no se puede escribir código que dependa de ella.
Lo que sí se puede hacer, y es lo correcto, es tratarla como una mejora. Su modo de fallo es cosmético: sin ella, el elemento cambia de altura de golpe en lugar de animarse. Nada deja de funcionar, nada queda ilegible, nadie pierde acceso a nada. Eso la coloca en la categoría de las capacidades que se adoptan hoy con un camino base sencillo.
Hay un detalle del modo de fallo que no aparece en las tablas de soporte y que produce un resultado más molesto que la ausencia total. Cuando escribes height: auto en el estado abierto y el motor no soporta interpolate-size, la propiedad height no interpola, correcto. Pero si en la misma regla tienes otras propiedades que sí interpolan —una opacidad, un desplazamiento, un padding— esas sí se animan, y lo que ve el usuario es un elemento que aparece a su altura completa de golpe mientras su contenido se desvanece suavemente hacia dentro. Es decir, obtienes lo peor de las dos opciones: el salto brusco que querías evitar más una animación que ahora no encaja con nada, porque estaba diseñada para acompañar a un cambio de altura que no ocurre. Con un acordeón dentro de una lista, el efecto es que las filas de debajo pegan un salto instantáneo mientras el contenido recién revelado se está desvaneciendo, y la incoherencia es mucho más visible que un simple salto limpio. La lección práctica es que la detección con @supports no es opcional aquí, aunque el fallo sea cosmético: no basta con escribir height: auto y confiar en que se degrade bien, porque lo que se degrada mal es la coordinación con el resto de la animación. En el camino base tienes que decidir explícitamente qué hace el resto de las propiedades cuando la altura no se anima, y casi siempre la respuesta correcta es que tampoco se animen, para que el cambio sea un salto honesto y no una mezcla.
El patrón de mejora progresiva
La detección es una regla condicional, y la forma correcta es escribir primero un camino base que funcione en los cuatro motores y encima la mejora.
/* Camino base: la tecnica de rejilla, portable. */
.acordeon-cuerpo {
display: grid;
grid-template-rows: 0fr;
transition: grid-template-rows 300ms cubic-bezier(0.2, 0, 0, 1);
}
.acordeon-cuerpo > * {
min-height: 0;
overflow: hidden;
}
.acordeon[data-abierto] .acordeon-cuerpo {
grid-template-rows: 1fr;
}
/* Mejora: donde exista, la version directa sin envoltorio extra. */
@supports (interpolate-size: allow-keywords) {
.acordeon-cuerpo {
display: block;
height: 0;
overflow: hidden;
transition: height 300ms cubic-bezier(0.2, 0, 0, 1);
}
.acordeon-cuerpo > * {
min-height: auto;
overflow: visible;
}
.acordeon[data-abierto] .acordeon-cuerpo {
height: auto;
}
}
:root {
interpolate-size: allow-keywords;
}
Ese bloque es más largo de lo que a nadie le gustaría, y esa es exactamente la razón por la que en la mayoría de los proyectos la decisión correcta hoy es quedarse con el camino base y no escribir la mejora. La técnica de rejilla funciona en los cuatro motores, no exige detección y su resultado visual es indistinguible. La mejora solo compensa cuando el envoltorio adicional estorba de verdad, por ejemplo cuando el elemento tiene que participar en un grid o un flex del contenedor padre y el envoltorio rompe esa participación.
Para casos donde la mejora sí compense, la detección desde JavaScript:
const puedeAuto = CSS.supports('interpolate-size', 'allow-keywords');
Qué esperar de aquí en adelante
Merece la pena una nota sobre cómo evaluar este tipo de capacidades, porque el patrón se repite. Una capacidad implementada en un solo motor durante dos años puede acabar en tres sitios distintos: llegar a los demás, quedarse como una peculiaridad de un motor, o ser sustituida por otra cosa. interpolate-size está en el primer caso con bastante probabilidad, porque resuelve un problema universalmente reconocido, tiene una especificación estable y hay interés declarado en los otros motores.
Pero “probablemente llegue” no es un criterio para escribir código hoy. El criterio es el de siempre: qué ve el usuario si no está, y aquí la respuesta es “un salto en lugar de una animación”, que es aceptable si has escrito el camino base de forma coherente.
- Implementa un acordeón con la técnica de rejilla y otro con
interpolate-size. Compara el resultado visual en Chromium. - Prueba los dos en un motor sin
interpolate-sizey describe exactamente qué ves en cada uno. - Quita el
@supportsde la versión mejorada y añade una animación de opacidad. Comprueba el efecto incoherente descrito en esta lección. - Decide, para un proyecto tuyo concreto, si la mejora compensa el bloque adicional, y escribe la razón en una frase.