Resultados rápidos con Flexible Box Model

HTML5 Rocks

Introducción

Probablemente hayas trabajado más de una vez en la definición del estilo de los elementos que ocupan el espacio horizontal o vertical de una página. Sin embargo, CSS no cuenta todavía con un mecanismo adecuado para realizar esta tarea. Por ello, te recomendamos que utilices el módulo Flexible Boxde CSS3 (o Flexbox, de forma abreviada).

En el borrador, se describe Flexbox como:

[...] un modelo de cajas de CSS optimizado para diseño de interfaces. Flexbox proporciona un sistema de diseño adicional a los que ya ofrece CSS. [CSS21] En este nuevo modelo de cajas, los elementos secundarios de una caja se disponen tanto horizontal como verticalmente, y el espacio no utilizado puede asignarse a un elemento secundario específico o distribuirse entre los diferentes elementos secundarios mediante la asignación de "flex" a los elementos secundarios que se deben expandir. El anidamiento de estas cajas (horizontal dentro de vertical o vertical dentro de horizontal) se puede utilizar para crear diseños en dos dimensiones. Flexbox se basa en el modelo de cajas del lenguaje de interfaz de usuario XUL que se utiliza en la interfaz de usuario de un gran número de aplicaciones basadas en Mozilla (como Firefox).

Estupendo. Para ti (como desarrollador, no como creador de diseños), esto significa lo siguiente:

  1. No hace falta incluir propiedades "float".
  2. Los diseños que antes suponían un difícil reto ahora parecen más viables.
  3. Podemos crear diseños verdaderamente flexibles y dejar que el navegador haga los cálculos por nosotros.

Flexbox ofrece un nuevo valor para la propiedad display (el valor box) y ocho propiedades nuevas:

  • box-orient
  • box-pack
  • box-align
  • box-flex
  • box-flex-group
  • box-ordinal-group
  • box-direction
  • box-lines
¿Ocho propiedades nuevas? Resulta un poco abrumador, ¿verdad? Vamos a explicarlo.

Propiedades de estilo comunes de Flexbox

Estilos utilizados en la caja

display: box
Este nuevo valor para el estilo de visualización habilita este elemento y los elementos secundarios directos dentro de Flexible Box Model. El modelo Flexbox solo funciona con elementos secundarios directos.
box-orient
Valores: horizontal | vertical | inherit
¿Cómo se deben alinear los elementos secundarios de la caja? Hay dos valores adicionales (inline-axis, el valor real predeterminado, y block-axis), pero se asignan a la orientación horizontal y vertical, respectivamente.
box-pack
Valores: start | end | center | justify
Define la alineación del la caja a lo largo del eje definido por box-orient. Por tanto, si la orientación definida por box-orient es horizontal, esta propiedad determinará la forma de alineación horizontal de los elementos secundarios de la caja, y viceversa.
box-align
Valores: start | end | center | baseline | stretch
Básicamente, es la propiedad secundaria de box-pack. Define la forma de alineación de los elementos secundarios en la caja. Si la orientación es horizontal, esta propiedad determinará la alineación vertical, y viceversa.

Estilos utilizados en los elementos secundarios de la caja

box-flex
Valores: 0 | Un número entero
Indica el índice de flexibilidad del elemento secundario. Si el valor de un elemento secundario es 1 y el de otro elemento secundario es 2, este último consumirá el doble de espacio adicional de la caja principal. El valor predeterminado es 0, lo que indica que no es flexible.

No se han incluido las propiedades box-flex-group, box-ordinal-group, box-direction y box-lines, porque realmente no vas a necesitarlas para la mayor parte del trabajo que harás con Flexbox. Para ver cómo se utilizan estas propiedades, consulta los enlaces incluidos en la sección Resumen.

Nota sobre la sintaxis: actualmente, para implementar Flexbox en WebKit y Gecko, se deben utilizar prefijos del proveedor. En este tutorial, no se ha incluido casi ningún prefijo por claridad. Para obtener más información, consulta la sección Compatibilidad con el navegador.

¿Qué es la flexibilidad?

La propiedad de estilo box-flex determina si un elemento secundario de una caja flexible debe ser flexible o no y ayuda a definir su índice de flexibilidad en relación con el resto de elementos secundarios. Veamos un ejemplo práctico para entender lo que significa esto. Empezaremos con tres cajas.
<div id="flexbox">
  <p>child 1</p>
  <p>child 2</p>
  <p>child 3</p>
</div>

A continuación, las colocaremos horizontalmente, una junto a otra. Las alturas de las cajas deben coincidir siempre, independientemente del contenido de cada una. ¿Cómo se puede conseguir esto? Aparentemente, lo más fácil sería hacer flotar estos párrafos añadiendo, por ejemplo, overflow:hidden; al elemento principal para eliminar los elementos flotantes. Este sistema no tiene mucho misterio. Sin embargo, podemos conseguir lo mismo fácilmente con Flexbox:

#flexbox { 
  display: box;
  box-orient: horizontal;
}

En el fragmento de código que aparece arriba, se indica al elemento principal que se comporte de acuerdo con este modelo Flexbox y que todos los elementos secundarios se coloquen a lo largo del eje horizontal. Como se puede comprobar, no se utilizan elementos flotantes.

El ancho de los elementos secundarios se mantiene tal como se ha especificado (o se utiliza el ancho inherente, si no se ha especificado ninguno). Esto significa que, si el ancho total de todos los elementos secundarios es inferior al ancho total del elemento principal, obtendremos algo así:

los tres elementos secundarios mantienen los valores de ancho inherentes dentro del elemento principal

De forma predeterminada, los elementos secundarios de las cajas flexibles se mantienen inflexibles. Aunque esto pueda parecer algo extraño, de esta forma los elementos secundarios tienen la posibilidad de convertirse en flexibles. Pero, ¿qué ocurre si queremos que los elementos secundarios uno y dos tengan un ancho específico y que el elemento secundario tres ajuste su ancho en función del espacio disponible dentro del elemento principal? Flexbox es la solución:

#flexbox { 
  display: box;
  box-orient: horizontal;
}
#flexbox > p:nth-child(3) {
  box-flex: 1;
}

En este ejemplo, se indica al último elemento secundario que se haga flexible y que ocupe el espacio disponible. Como solo hemos asignado espacio a un elemento, este ocupará todo el espacio disponible:

el tercer elemento secundario, convertido en flexible, ocupa el espacio disponible

Ten en cuenta que el elemento solo se hace flexible a lo largo del eje de orientación de la caja (en este caso, el eje horizontal).

El valor de "box-flex" es relativo. Por tanto, si queremos que los elementos secundarios segundo y tercero sean flexibles, debemos hacerlo así:

#flexbox { 
  display: box;
  box-orient: horizontal;
}
#flexbox > p:nth-child(2),
#flexbox > p:nth-child(3) {
  box-flex: 1;
}

De esta forma, cada elemento ocupará la misma cantidad de espacio disponible, que se dividirá equitativamente entre los elementos.

dos de los tres elementos secundarios comparten el espacio disponible en el elemento principal
También podemos establecer los valores 1, 2 y 3, respectivamente, para la propiedad box-flex de los elementos secundarios uno, dos y tres, de forma que estos elementos ocupen proporcionalmente el espacio adicional del elemento principal. Veamos un caso práctico.

Un ejemplo básico

Consulta el código que aparece a continuación y el resultado que se obtiene:

Coloca el cursor sobre una de las cajas para ver cómo funciona Flexbox. A medida que una caja se expande, los demás se encogen, pero el ancho total siempre coincide con el tamaño de la caja principal.

En realidad, solo se utilizan dos estilos: display: box, que hace que se utilice el modo de cajas flexibles, y box-flex: 1, que hace que los elementos secundarios funcionen en modo flexible ocupando todo el espacio sobrante. La orientación predeterminada es horizontal. Por tanto, aunque no es necesario utilizar el estilo box-orient: horizontal, se recomienda incluirlo por motivos de claridad y sostenibilidad. El estilo box-align predeterminado es alargado, por lo que los elementos "div" ocupan toda la altura de la caja principal. No está mal, ¿verdad? Para ver cómo se utiliza esta técnica en la navegación, consulta esta demostración de navegación flexible de Raphael Goetter.

Llevemos esta técnica a otro nivel.

Cómo colocar un elemento en el centro

Siempre ha sido un reto centrar un elemento de forma horizontal y vertical en CSS. La mejor solución específica para CSS consiste en utilizar la fórmula position:absolute; left: 50%; top: 50%;, junto con valores negativos para los márgenes izquierdo y superior que sean iguales a la mitad de los valores de ancho/altura. Pero esta fórmula solo funciona con elementos de tamaño específico. ¡Vaya!

James John Malcom escribió que existe una forma de alinear elementos verticalmente basada en display:table-cell; que se inventó hace al menos seis años (Dušan Janovský escribió sobre ello en 2004). Para consultar el artículo completo sobre esta solución de alineación horizontal y vertical, haz clic aquí. Este método funciona incluso con elementos que no tienen un tamaño específico.

Con Flexbox, podemos centrar un elemento con mayor facilidad:

No se establece la propiedad box-flex en el elemento secundario porque no queremos que utilice el espacio sobrante. Queremos colocarlo en el centro, independientemente de su tamaño. Esta es la gran ventaja que ofrece este sistema: no es necesario que un elemento tenga unas dimensiones específicas para poder centrarlo. Se pueden centrar elementos que normalmente se encuentran en bloque o integrados. Haz la prueba y verás como funciona.

Compatibilidad con el navegador

¿Los usuarios podrían utilizar actualmente el modelo Flexbox en su trabajo? Depende del navegador que utilicen. Hasta ahora, no tenemos constancia de que Flexbox se haya utilizado en Internet Explorer 9 o en Opera 10.60, pero sí que ha aparecido en una de las vistas previas de la plataforma de Internet Explorer 9, por lo que es probable que Microsoft lo añada en algún momento.

En la página Caniuse.com, podrás encontrar información sobre los navegadores compatibles, que básicamente son Firefox 3 y versiones posteriores, Safari 3 y versiones posteriores y Chrome. Si te dedicas al desarrollo de WebKit para móviles, Flexbox puede ser una magnífica alternativa a tus esquemas de diseño estándares.

Como este modelo es experimental, te recomendamos que utilices los prefijos del proveedor:

/* i wish it was as easy as this: */

display: box;
box-orient: horizontal; 
box-pack: center;
box-align: center;
  
/* but in reality you'll need to do this: */

display: -webkit-box;
-webkit-box-orient: horizontal;
-webkit-box-pack: center;
-webkit-box-align: center;

display: -moz-box;
-moz-box-orient: horizontal;
-moz-box-pack: center;
-moz-box-align: center;

display: box;
box-orient: horizontal;
box-pack: center;
box-align: center;
  

Si esto te parece demasiado complejo, puedes consultar un material de ayuda de gran utilidad que incluye un resumen de todas estas opciones, preparado por Alex Russell.

Resumen

Flexbox ofrece una gran cantidad de posibilidades, incluso sin tener en cuenta las otras cuatro propiedades. Para obtener más información sobre Flexbox, consulta las demostraciones de Flexbox de la página Isotoma y las publicaciones de la página Mozilla Hacks sobre Flexbox. Si tienes fuerzas suficientes para leer un texto denso, podrás encontrar más información en las especificaciones de Flexbox de W3C. ¡Anímate a crear algunos diseños!

Algunas partes de este tutorial se basan en una guía de Stephen Hay, que autorizó la distribución de su trabajo con una licencia CC-by.

Comments

0