¿Cómo puedo combinar flexbox y desplazamiento vertical en una aplicación de altura completa?

101

Quiero usar una aplicación de altura completa usando flexbox. Encontré lo que quiero usando el antiguo módulo de diseño de flexbox ( display: box;y otras cosas) en este enlace: aplicación CSS3 Flexbox de altura completa y desbordamiento

Esta es una solución correcta para los navegadores que solo admiten la versión anterior de las propiedades CSS de flexbox.

Si quiero intentar usar las propiedades de flexbox más nuevas, intentaré usar la segunda solución en el mismo enlace que aparece como truco: usar un contenedor con height: 0px;. Hace mostrar un desplazamiento vertical.

No me gusta mucho porque presenta otros problemas y es más una solución que una solución.

html, body {
    height: 100%;    
}
#container {
	display: flex;
	flex-direction: column;
	height: 100%;
}
#container article {
	flex: 1 1 auto;
	overflow-y: scroll;
}
#container header {
    background-color: gray;
}
#container footer {
    background-color: gray;
}
<section id="container" >
    <header id="header" >This is a header</header>
    <article id="content" >
        This is the content that
        <br />
        With a lot of lines.
        <br />
        With a lot of lines.
        <br />
        This is the content that
        <br />
        With a lot of lines.
        <br />
        <br />
        This is the content that
        <br />
        With a lot of lines.
        <br />
        <br />
        This is the content that
        <br />
        With a lot of lines.
        <br />
    </article>
    <footer id="footer" >This is a footer</footer>
</section>

También he preparado un JSFiddle con un ejemplo base: http://jsfiddle.net/ch7n6/

Es un sitio web HTML de altura completa y el pie de página está en la parte inferior debido a las propiedades flexbox del elemento de contenido. Le sugiero que mueva la barra entre el código CSS y el resultado para simular una altura diferente.

José Cabo
fuente
¿Este no es el comportamiento que estás buscando? jsfiddle.net/ch7n6/2
cimmanon
2
jsfiddle.net/ch7n6/3 ¡Sí! Es. : D Pero no entiendo por qué necesito indicar una altura para obtener el efecto. Configuración de todos modos: altura: 1px; obras
José Cabo
Ahora cambié la altura a una altura mínima. Mucho mejor. Gracias.
José Cabo
1
@ JoséCabo +1 - buena altura del truco: 0 para mostrar el desplazamiento vertical. ¿Podría explicar por qué funciona esto?
Danield
1
Debe aplicar flex-shrink:0tanto al encabezado como al pie de página.
Saorikido

Respuestas:

202

Gracias a https://stackoverflow.com/users/1652962/cimmanon que me dio la respuesta.

La solución es establecer una altura para el elemento desplazable vertical. Por ejemplo:

#container article {
    flex: 1 1 auto;
    overflow-y: auto;
    height: 0px;
}

El elemento tendrá altura porque flexbox lo vuelve a calcular a menos que desee una altura mínima para que pueda usar height: 100px;que sea exactamente igual que:min-height: 100px;

#container article {
    flex: 1 1 auto;
    overflow-y: auto;
    height: 100px; /* == min-height: 100px*/
}

Entonces, la mejor solución si desea un min-heightdesplazamiento vertical:

#container article {
    flex: 1 1 auto;
    overflow-y: auto;
    min-height: 100px;
}

Si solo desea un desplazamiento vertical completo en caso de que no haya suficiente espacio para ver el artículo:

#container article {
    flex: 1 1 auto;
    overflow-y: auto;
    min-height: 0px;
}

El código final: http://jsfiddle.net/ch7n6/867/

José Cabo
fuente
2
El uso min-heighten Chrome no funciona, afecta el tamaño del pie de página de alguna manera. Usando heightsin embargo, da el resultado deseado.
phant0m
1
Trate de colocar esa altura en donde el "auto". He estudiado esto y creo que el lugar correcto es esta propiedad. Entonces, en lugar de usar min-height y height, utilícelo.
José Cabo
height: 0Se corrigieron algunos saltos de 2px cuando el contenido se desbordaba frente a cuando no. Tan raro. Gracias de todos modos.
ProblemsOfSumit
@Sumit, ¿puede darnos una idea del problema al que se enfrenta?
José Cabo
Abrí el enlace del violín y parece que ya no funciona en Chrome (funciona en Firefox). La barra de desplazamiento desapareció. ¿Alguien tiene una idea de cómo hacer que esto vuelva a funcionar?
apuestas
61

Editor de especificaciones de Flexbox aquí.

Este es un uso recomendado de flexbox, pero hay algunas cosas que debe modificar para lograr un mejor comportamiento.

  • No use prefijos. Flexbox sin prefijo es compatible con la mayoría de los navegadores. Siempre comience sin prefijos y solo agregue prefijos si es necesario para admitirlo.

  • Dado que su encabezado y pie de página no están destinados a flexionarse, ambos deberían haberse flex: none;establecido en ellos. En este momento, tiene un comportamiento similar debido a algunos efectos superpuestos, pero no debe confiar en eso a menos que desee confundirse accidentalmente más tarde. (El valor predeterminado es flex:0 1 auto, por lo que comienzan en su altura automática y pueden encogerse pero no crecer, pero también lo son overflow:visiblede forma predeterminada, lo que activa su valor predeterminado min-height:autopara evitar que se encojan en absoluto. Si alguna vez establece un valor overflowen ellos, el comportamiento de los min-height:autocambios (cambiando a cero en lugar de contenido mínimo) y de repente serán aplastados por el <article>elemento extra alto ).

  • También puede simplificarlo <article> flex, simplemente configúrelo flex: 1;y estará listo para comenzar . Intente ceñirse a los valores comunes en https://drafts.csswg.org/css-flexbox/#flex-common a menos que tenga una buena razón para hacer algo más complicado: son más fáciles de leer y cubren la mayoría de los comportamientos querrás invocar.

Xanthir
fuente
21

La especificación actual dice esto con respecto a flex: 1 1 auto:

Dimensiona el elemento según las propiedades width/ height, pero los hace completamente flexibles, de modo que absorben cualquier espacio libre a lo largo del eje principal. Si todos los elementos son o bien flex: auto, flex: initialo flex: none, cualquier espacio libre positivo después de que los artículos han sido dimensionadas será distribuido de manera uniforme a los elementos con flex: auto.

http://www.w3.org/TR/2012/CR-css3-flexbox-20120918/#flex-common

Me parece que si dices que un elemento tiene 100 píxeles de alto, se trata más como un tamaño "sugerido", no como un absoluto. Debido a que se le permite encogerse y crecer, ocupa tanto espacio como se le permite. Es por eso que agregar esta línea a su elemento "principal" funciona: height: 0(o cualquier otro número más pequeño).

cimmanon
fuente