Bloques desplegables con Grid de CSS

En las páginas web los elmentos o bloques desplegables son muy útiles para guardar contenido y desplegarlo a elección del usuario. Son esos bloques con una cabecera que al ser pulsada despliegan por debajo una elemento con algun contenido: texto, enlaces, imágenes...

En esta sección tienes otro bloque desplegable pero en este que te muestro aquí el método de plegar desplegar está en la cabecera que actúa como un toggle.

Un uso muy habitual son los llamados accordions: bloques de text que se muestran u ocultan al pulsar un botón. En eta misma sección tienes una forma de crear un accordion con css/html. Es fácil veros en secciones FAQS: la cabecera es la pregunta y el cuerpo es la respuesta.

Pero también los podemos ver en menús: una cabecera que al ser pulsada muestra una lista de enlaces

Hay bastatnes usos: siempre que queramos mantener oculto un contenido y motrarlo a voluntad podemos utilizar este efecto de bloque desplegable.

No se usa javascript, entonces como elemento activo para abrir o cerrar el bloque usamos un control tipo checkbox, y hacemos uso de los selectores para elementos adyacentes o hijos

Crear bloque Web desplegable con GRID

Código HTML

El código HTML no tiene ninguna particularidad. El bloque desplegable está formado por una

  • Cabecera: un titulo y un botón input, al pulsar desplegamos/plegamos el contenido
  • Contenido: el loque con el contenido que desepliega o cierra

Estos bloques están dentro de un contenedor al que asignamos la clase dropdown

La clave está en el input: la posibilidad de poder definir estilos CSS en función de si está o no activado es lo que permite que este despliegue funcine sin javascript

<div class="dropdown">

<label for="toggle" class="header">Cabecera</label>

<input type="checkbox" id="toggle" class="toggle">

<div class="content">

<div>

<p>Contenido panel linea 1</p>

<p>Contenido panel linea 2</p>

<p>O lo que quieras</p>

</div>

</div>

Los estilos CSS

El estilo CSS utiliza el layout grid con este tipo de layout podremos hacer que el bloque despelgable se ajuste a su contenido. el largo no tiene que ser fijo, y el navegador lo ajusta automáticamente. Esta es la otra clave para el buen funcionamiento de este efecto.

El selector dropdown es el contendor de todo el desplegable. Con este definimos el ancho del bloque. Ponemos posicion relativa, para que sea la referencia de los elementos en posición absoluta que vamos a necesitar.

Luego tenemos que definir el estilo para la cabecera, este selector lo usamos para definir el aspecto de la cabecera del bloque, el lugar donde pulsaremos para abrirlo y cerrarlo. El control input, tipo checkbox, no lo vamos a mostrar, se activa pulsando sobre la cabecera que es el label de ese input.

Por último tenemos el estilo para el blqoue de conenido, el que se va a desplegar o replegar. Esta operación está animada y se consigue con el alto de las filas del grid. En replegado este grid tiene un alto de 0fr, mientras que desplegado es 1fr, es decir todo el espacio necesario para su contenido. No tenemos que preocuparnos de su altura, ya lo hace el navegador al aplicar el grid. ¿No es genial?

Si el boton está pulsado se aplica el estilo toggle:checked + .content y si no pues se aplica solo .toggle .content

Habitualmente estos bloques llevan un icono o algún simbolo para indicar cuando está replegado (+) o desplegado (-). Para esto he elegido colocar un pseudo elemento ::before para .content. Mediante este elemento agregamos un contenido que puede ser + o -, o X/O o un icono. Por simplicidad he puesto + - . La posición de este elemento es absoluta, y su posición se refiere al elemento relativo más próximo: la cabecera (.header). Lo colocamos a right: 2px y top: 0. Esto ya es libre.

Lo único fundamental aquí es grid-template-rows que pasa de 0fr a 1fr, desde altura 0 (contraído) a altura 1fr (desplegado)

Puedes probarlo y darle colores paddings, margins o lo que quieras para adaptarlo a donde vayas a utilizarlo.

@charset "utf-8";

.dropdown{

width: 200px;

position: relative;

margin: 4px;

}

.header{

display: block;

width: 100%;

cursor: pointer;

background:rgba(200,200,200,1.00);

position: relative;

}

.content {

display: grid;

grid-template-rows: 0fr;

width: 100%;

background: rgba(230,231,223,1.00);

transition: grid-template-rows 300ms;

}

.toggle{

display: none;

}

.toggle + .content::before{

position: absolute;

content : "+";

right:2px;

top: 0

}

.toggle:checked + .content::before{

content : "-";

}

.toggle:checked + .content {

grid-template-rows: 1fr;

}

.content >div {

overflow: hidden

}