Platzi
Platzi

Suscríbete a Expert y aprende de tecnología al mejor precio anual.

Antes:$249
$209
Currency
Antes:$249
Ahorras:$40
COMIENZA AHORA
172

Guía de BEM para CSS | Cohete Falcon 9 de SpaceX

8455Puntos

hace 4 meses

Curso de Frontend Developer 2019
Curso de Frontend Developer 2019

Curso de Frontend Developer 2019

Domina las bases de HTML y CSS. Define la arquitectura de tu código y construye un sitio web usando componentes estáticos. Maqueta las pantallas principales de tu página web. Agrega diseño responsivo y usa preprocesadores para optimizar tu código CSS. ¡Conviertete en Frontend Developer con Platzi!

BEM es una convención o metodología para nombrar tus clases de CSS. Por sus siglas en inglés, BEM significa Bloque, Elemento y Modificador.

En esta guía aprenderemos:

  • Cómo funciona BEM
  • Cómo usar BEM en CSS
  • Por qué y para qué usar BEM
  • Ejemplo prácticos de BEM (incluyendo un cohete Falcon 9 de Space X) 🚀
  • 3 casos con lo que debes y no debes hacer con BEM
  • 3 problemas comunes en BEM y cómo solucionarlos
  • BEM + SASS
  • Recomendaciones finales

¿Cómo funciona BEM?

BEM funciona identificando el bloque, el elemento y el modificador de un componente.

  • Bloque es el contenedor principal del componente.
  • Elemento son las partes internas que conforman el componente.
  • Modificador son las variaciones del bloque o del elemento.

El cohete Falcon 9 de SpaceX está compuesto por varias partes que hacen posible el transporte confiable y seguro de personas o cargas útiles a la órbita terrestre (incluso más allá). Para cada una de las partes podemos crear una analogía.

Vamos a identificar quién sería el elemento bloque, quiénes serían los elementos y quiénes serían los modificadores, así:

Teniendo entonces:

  • Bloque: Falcon 9
  • Elementos: First stage, Interstage, Second stage.
  • Modificador: Fairing, Dragon.

Después de revisar la analogía con el cohete Falcon 9, revisemos algunos ejemplos que podemos encontrarnos en la vida real:

  • Bloque: card, button, form, menu, header…
  • Elemento: icon, text, item, image, input, button…
  • Modificador: active, big, right, secondary, red…

😍

Cómo se usar BEM en CSS

Los nombres de clases con convención BEM,pueden tener la siguiente sintaxis:

  • [bloque]
  • [bloque]__[elemento]
  • [bloque]--[modificador]
  • [elemento]--[modificador]
  • [bloque]__[elemento]--[modificador]

Teniendo en cuenta lo anterior, el CSS para nuestro Falcon 9 se escribiría así:

  • .falcon9 { ... }
  • .falcon9--fairing { ... }
  • .falcon9--dragon { ... }
  • .falcon9__first-stage { ... }
  • .falcon9__interstage { ... }
  • .falcon9__second-stage { ... }

Y así se vería el HTML:

<rocketclass="falcon9 falcon9--dragon"><stageclass="falcon9__first-stage"></stage><stageclass="falcon9__interstage"></stage><stageclass="falcon9__second-stage"></stage></rocket>

Además, el CSS siguiendo BEM con un ejemplo de la vida real se escribiría así:

  • .button { ... }
  • .button--active { ... }
  • .button__icon { ... }
  • .button__text { ... }

Y así se vería el HTML:

<buttonclass="button button--active"><iclass="button__icon"></i><spanclass="button__text"></span></button>

⚠️ Importante: recuerda que:

  • Los guiones bajos (__) se usan para separar el bloque del elemento,
  • Los guiones medios (--) se usan para separar el bloque o el elemento del modificador.

💡 Nota: BEM permite cambiar esta nomenclatura. También puedes encontrar nombres de clase así: [bloque]__[elemento]-[modificador], [bloque]__[elemento]_[modificador], entre otros. Lo más importante a la hora de usar una de estas nomenclaturas es ser consistente en todo el proyecto.

¿Por qué y para qué usar BEM?

Tal vez te preguntes, “Pero, ¿Teff, para qué seguir esta metodología si el resultado en CSS es el mismo? ¡Solo estamos haciendo más trabajo!”

  1. Para tener un CSS más fácil de leer, entender, mantener y escalar.
  2. Para organizar las clases de CSS en módulos independientes.
  3. Para evitar selectores de CSS anidados.

Casos prácticos de BEM

Card:

Identifiquemos el bloque, los elementos y los modificadores (si los tiene) de la siguiente card:

De la imagen anterior, tenemos lo siguiente:

  • Bloque: card
  • Elementos: image, text
  • Modificadores: (no tiene)

Su estructura de HTML con la convención de clases BEM, sería:

<div class="card">
    <imgclass="card__image"src="/image.png"alt="spacesuit" /><pclass="card__text"></p><pclass="card__text"></p></div>

Navbar:

Identifiquemos el bloque, los elementos y los modificadores (si los tiene) del siguiente navbar:

De la imagen anterior, tenemos lo siguiente:

  • Bloque: navbar
  • Elementos: logo, items
  • Modificadores: gray

Su estructura de HTML con la convención de clases BEM, sería:

<nav class="navbar">
    <ul class="navbar">
        <liclass="navbar__item"><i class="navbar__icon"></i></li>
        <liclass="navbar__item">MENS</li>
        <liclass="navbar__item">WOMENS</li>
        <liclass="navbar__item">KIDS</li>
        <liclass="navbar__item">ACCESSORIES</li>
        <liclass="navbar__item">PREMIUM</li>
        <liclass="navbar__item navbar__item--gray">ACCOUNT</li>
        <liclass="navbar__item navbar__item--gray">SEARCH</li>
        <liclass="navbar__item">CART (0)</li>
    </ul>
</nav>

Section:

Identifiquemos el bloque, los elementos y los modificadores (si los tiene) de la siguiente sección:

Como de la imagen anterior identificamos 2 bloques, vamos a dividir la estructura en 2 partes, así:

Para el bloque 1:

  • Bloque: section
  • Elementos: text, image
  • Modificadores: primary, secondary-semibold, secondary-bold

Para el bloque 2:

  • Bloque: list
  • Elementos: item, text
  • Modificadores: gray

La estructura de HTML con la convención de clases BEM para ambos bloques, sería:

<sectionclass="section"><div><h2class="section__text section__text--primary">FALCON 9</h2><pclass="section__text section__text--secondary-semibold">Falcon 9, the world's first orbital class reusable rocket...</p><pclass="section__text section__text--secondary-bold">Learn more about Falcon 9</p><ulclass="list"><liclass="list__item"><spanclass="list__text">VEHICLE HEIGHT</span><div><spanclass="list__text">70m</span><spanclass="list__text list__text--gray">/229.6 ft</span></div></li><liclass="list__item"><spanclass="list__text">VEHICLE DIAMETER</span><div><spanclass="list__text">3.7m</span><spanclass="list__text list__text--gray">/12 ft</span></div></li><liclass="list__item"><spanclass="list__text">FAIRING HEIGHT</span><div><spanclass="list__text">13.1m</span><spanclass="list__text list__text--gray">/43 ft</span></div></li><liclass="list__item"><spanclass="list__text">FAIRING DIAMETER</span><div><spanclass="list__text">5.2m</span><spanclass="list__text list__text--gray">/17.1 ft</span></div></li></ul></div><div></div></section>

Casos con lo que debes y no debes hacer con BEM

1️⃣ Primer caso

  • Lo que sí: dejar la clase principal card y añadir otra clase con modificador.
<div class="card card--flat"></div>
  • Lo que no: usar la clase con modificador como clase principal.
<div class="card--flat"></div>

2️⃣ Segundo caso

  • Lo que sí: no representar los niveles de profundidad de HTML con BEM.
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /><pclass="card__text"><iclass="card__icon"></p></div>
  • Lo que no: representar los niveles de profundidad de HTML con BEM.
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /><pclass="card__text"><iclass="card__text__icon"></p></div>

3️⃣ Tercer caso

  • Lo que sí: incluir la clase en un hijo que necesita estilos.
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /></div><style>
    .card { ... }
    .card__image { ... }
</style>
  • Lo que no: Omitir la clase en un hijo que necesita estilos.
<divclass="card"><imgsrc="/image.png"alt="Crew Dragon" /></div><style>
    .card { ... }
    .card img { ... }
</style>

3 problemas comunes con BEM y cómo solucionarlos

1️⃣ Primer caso

  • Problema: tengo un componente A que ya tiene sus propias clases y deseo añadirlo a un nuevo componente B. ¿Debo agregar una nueva convención para el componente A que estará dentro de B?

Componente A:

<buttonclass="button button--active"></button>

Componente B:

<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /></div>
  • Solución: puedes dejar el componente A con las clases que ya estaban establecidas así no sean coherentes con el nuevo componente B, por ejemplo:
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /><buttonclass="button button--active"></button></div>

2️⃣ Segundo caso

  • Problema: en mi estructura de HTML tengo padres, hijos, nietos, tataranietos, etc; pero BEM sólo me deja usar 3 niveles. ¿Qué hago con los elementos nietos y sus descendientes?
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /><divclass="card__footer"><pclass="card__footer__text"><iclass="card__footer__text__icon"><p></div></div>
  • Solución: como lo mencionamos anteriormente, BEM no representa los niveles de tu estructura de HTML. Lo ideal en este caso sería tener:
<divclass="card"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /><divclass="card__footer"><pclass="card__text"><iclass="card__icon"><p></div></div>

3️⃣ Tercer caso

  • Problema: quiero utilizar la propiedad display: none para ocultar desde JavaScript un componente de Card y un componente de Botón. ¿Debo crear una clase para cada componente siguiendo su propia estructura de BEM (card--hidden y button--hidden)?
<divclass="card card--hidden"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /></div><buttonclass="button button--hidden"></button><style>.card--hidden {
        display: none;
    }
    .button--hidden {
        display: none;
    }
</style>
  • Solución: puedes crear una clase independiente a la estructura de BEM para aplicar propiedades generales, así, reducirás la cantidad de líneas de JavaScript ya que no tendrás que usar una clase específica para cada componente.
<divclass="card hidden"><imgclass="card__image"src="/image.png"alt="Crew Dragon" /></div><buttonclass="button hidden"></button><style>.hidden {
        display: none;
    }
</style>

• BEM + SASS

Dragon es la primera nave espacial privada en llevar humanos a la estación espacial. Pero, no lo hace sola. Dragon trabaja en conjunto con el cohete Falcon 9 para tener un lanzamiento perfecto.

Así como Dragon y Falcon 9 trabajan juntos, BEM y SASS también. SASS es un preprocesador de CSS que te permite anidar selectores, crear bucles, funciones, entre otras cosas. Y, adicionalmente, gracias a la sintaxis de SASS, podemos tener una combinación perfecta en nuestras hojas de estilos.

Por ejemplo, uno de nuestros ejercicios anteriores fue el siguiente:

<div class="card">
    <imgclass="card__image"src="/image.png"alt="Crew Dragon" /><buttonclass="button button--active"></button></div>

Donde, el CSS se ve de la siguiente forma:

.card {
    ...
}
.card__image {
    ...
}
.button {
    ...
}
.button--active {
    ...
}

Pero si usamos SASS, nuestros estilos se verían de la siguiente forma:

.card {
    &__image {
        ...
    }
}
.button {
    &--active {
        ...
    }
}

Aquí sólo alcanzamos a reducir 2 líneas de código, pero, ¿te alcanzas a imaginar cuántas líneas de código podríamos ahorrarnos en un proyecto con mucho más HTML y CSS? Este es uno de los súper poderes de combinar BEM con SASS, aparte de que se ve mucho más lindo y limpio nuestro código.

Recomendaciones finales

Los proyectos que usan BEM son fáciles de leer, muy intuitivos y permiten evitar los selectores de CSS anidados. También, es una herramienta que permite personalizar las reglas y nomenclatura para tener un código mucho más limpio y escalable.

Recursos de imágenes: https://www.spacex.com

Si quieres aprender todo lo necesario para convertirte en Frontend Developer construyendo un proyecto profesional desde cero, te espero en el Curso de Frontend Developer en Platzi.

Curso de Frontend Developer 2019
Curso de Frontend Developer 2019

Curso de Frontend Developer 2019

Domina las bases de HTML y CSS. Define la arquitectura de tu código y construye un sitio web usando componentes estáticos. Maqueta las pantallas principales de tu página web. Agrega diseño responsivo y usa preprocesadores para optimizar tu código CSS. ¡Conviertete en Frontend Developer con Platzi!
Estefany
Estefany
teffcode

8455Puntos

hace 4 meses

Todas sus entradas
Escribe tu comentario
+ 2
Ordenar por:
16
27035Puntos

Muy buena explicacion de como implementar BEM en CSS
Ahora Doge podrá tener su espacio organizado mas eficientemente.

space doge.jpg

No me pude resistir .

3
8455Puntos
4 meses

HAHAHA me encanta !!!

7

Muy bueno! estaba haciendo algunas cosas mal con BEM porque no lo tenia muy claro, ahora estoy al 100 ✓✓✓ y usarlo con SASS es lo mejor de todo 💚

3
8455Puntos
4 meses

Aiñ ! Me alegra mucho Sebas !!! 💚🚀✨

6

No es mejor hacer un curso de las metodologias aplicadas bem en proyectos. Seria bueno.

2
8455Puntos
4 meses

Uffff 🔥 con toda seguridad el team lo tendrá en cuenta ! Gracias Randyyy 💚🚀✨

4
6511Puntos

Excelente__Explicación–teff

2
8455Puntos
4 meses

Hahaha ! Graciasss mil Axeeel 💚🚀✨

3
11828Puntos

Excelente artículo mi estimada @teffcode. Como todo lo que haces. Verdaderamente dedicada en todo. Ya esta agregado a mis notas

3
8455Puntos
4 meses

Aiñ !!! Maravillosoooo 💚🚀✨

3
12963Puntos

Muchas gracias por este post, me sirvió para aclarar las dudas sobre que hacer con la sintaxis en bloques anidados.

2
8455Puntos
4 meses

Maravillosooooo 💚🚀✨Me alegra muchísimo !!!

3
6866Puntos

Gracias Teff, excelente explicación.
Tenía dudas con esta metodología pero ahora me siento más seguro con todos los ejemplos que pusiste.

2
8455Puntos
4 meses

Maravilloso Ulises… Me alegra mucho leer esooo 💚🚀✨

3
4767Puntos

habia pasado varios cursos y aún no entendía como usar el BEM, muchas gracias, muy bien explicado

2
8455Puntos
4 meses

Aiñ ! Con todo el gustooo 💚🚀✨

3
10431Puntos

Lo de SpaceX fue buen ejemplo

3
10449Puntos

Gracias Teff.
Excelente artículo. Lo estoy poniendo en práctica en este momento para una un proyecto de un reto Platzi en el que estoy participando.

2
8455Puntos
4 meses

Wow !!! Feliz de ver el resultado de tu proyecto Gustavoooo 💚🚀✨

3
5201Puntos

Excelente post!

2
8455Puntos
4 meses

Gracias Rigooo 💚🚀✨

3
15716Puntos

Ame este post. Realmente lo necesitaba

Estaba aplicando algunas cosillas mal. Ahora lo entendí mejor y puedo aplicarlo en mi proyecto aprovechando que estoy reescribiendo codigo xD ❤️

2
8455Puntos
4 meses

Wow, maravillosooooo esto Darkusss 💚🚀✨

3
3654Puntos

Solamente falto el dinosaurio que llevaban.

2
8455Puntos
4 meses

Hahahah ! awwwww, es ciertoooo… el mejor dino del mundo viajando al espacio 💚🚀✨ !

2
15879Puntos

¡Excelente artículo! Vengo usando BEM hace un tiempo, pero reconozco que algunos usos no los tenía tan claros y sigo repitiendo algunos de los errores mencionados.

Estoy practicando para reforzarlo, usado junto a SASS es magia pura 🌠🌠🌠🌠🌠

2
8455Puntos
4 meses

Maravilloso !!! Siempre estamos en constante aprendizaje 💚 Me alegra mucho que lo estés practicando para reforzarlo 💪🏼

1
15879Puntos
4 meses

¡Oh, Teff! No sé si vas a leer esto también pero quiero enviarte mi agradecimiento y mi admiración por tus cursos, los quizzes de github y todo el cariño y la dedicación que le pones a lo que haces.

Muchísima gracias 😄

2

Muy bueno! alguien ya replico esto en GitHub?

2
8455Puntos
4 meses

Sería súper !!! 💚🚀✨

2
11305Puntos

Justo había terminado el curso de Frontend! usaré este blog para complementar mis apuntes 😍