Block Element Modifier
BEM encourages developers to divide layouts into blocks and nested elements. As a strict rule, all selectors in a BEM have the same weight.
BEM encourages developers to divide layouts into blocks and nested elements. As a strict rule, all selectors in a BEM have the same weight.
A block is a standalone entity that is meaningful on its own.
An element is a part of a block and has no standalone meaning, while every element is semantically tied to its block.
A modifier is a ‘change’ happening to blocks or elements. A change of appearance, behavior or a state.
Since every selector has an equal weight, every developer working with such strucutre, should recognize their position, function and overall purpose. He/she only has to read the selector’s name.
As mentioned above, every standalone component that is meaningful on its own is considered a block.
Here is an example:
.card { height: 256px; width: 512px; border-radius: 8px; background-color: #f1f1f1; }
<div class="card"> </div>
A block on very rare occasions exists as a complete monolith without any additional parts or segments.
Thus our showcased ,s>card, in order to be more realistic, should have at least an image, title, description and a button.
The image, title, description and a button are all elements located inside the card. Let’s call them child components.
Now in BEM, elements’ class names are formed by taking the block name and supplementing it with two underscores, followed by the particular element name. Like this:
.card__image { width: 100%; aspect-ratio: 2 / 1; } .card__title { font-size: 16px; font-family: var(--secondary-font); } .card__desc { font-size: 12px; font-family: var(--primary-font); } .card__button { padding: 12px 24px; background-color: var(--primary-color); color: var(--neutral-color); }
<div class="card"> <img class="card__image" src="#"/> <h4 class="card__title">Title</h4> <p class="card__desc">Description</p> <a class="card__button" href="#">Button</a> </div>
Card can get in different states like active highlight or disabled, and using BEM convention, modifier class names are created by taking the block name or a block name with modifier adding to it two hyphens, followed by an modifier name. Like this:
.card__image--active { } .card__title--active { } .card__desc--active { } .card__button--active { }
or this
.card--active { } .card--disabled { } .card--highlighed { }
Let’s continue with our card example:
.card--active { background-color: #aaaaaa; } .card__image--active { filter: opacity (.8); } .card__title--active { color: var(--primary-color); } .card__desc--active { color: #8a8a8a; } .card__button--active { opacity: .8; }
<div class="card card--active"> <img class="card__image card__image--active" src="#"/> <h4 class="card__title card__title--active">Title</h4> <p class="card__desc card__desc--active">Description</p> <a class="card__button card__button--active" href="#">Button</a> </div>
Now the anwser to probably most important question. How to use this knowledge in designer’s daily work in UIdesign tools like Figma, Adobe XD, InVision, UXPin etc. or in delivering design tokens or any other design-related deliverables?
Well it’s actually quite straightforward.
When creating a button with a UI design tool, give button’s layer a name like card__button–active or button–primary–md–active.
When creating a design token for a color of a particular button, name it tok.button-color__primary–500 or when creating a variable, name it $color__secondary–100.
This is how BEM pretty much works. If you’d like to explore more technical matters, you can read all about them here.
I use feedback to improve UI Crux Platform. If you noticed a mistake, please report it.