How to modify multiple elements of a block with BEM CSS


Tags: css,block,element,modifier,bem

Problem :

Let us say I have the following setup,

.block
  .block__header
  .block__content
  .block__footer

Now I want to show an active state of this block. Let us say the block itself gets a green background and element 2 and 3 should get bold text. As I understand the philosophy of BEM, one should not use child selectors in order to keep the specificity as low as possible.

So is this really the way to do it?

.block.block--active
  .block__header
  .block__content.block__content--active
  .block__footer.block__footer--active

Update: and how would I write that solution in SASS (very new to it)? This my setup so far... if I can use nested selectors, what is best practice here?

.block {
  &--active {

  }
  &__header {

  }
  &__content {
    // active modifier of content
    &--active {
      font-weight: bold;
    }
    // would be the same as
    .block--active & {
      font-weight: bold;        
    }
    // but can i reference the active block somehow else in sass? 
    // & is a parent selector but i would need the parent of the parent here...
  }
  &__footer {
    &--active {

    }
  }
}


Solution :

The philosophy of BEM is about to keep blocks context free. The low specificity is just a good practice, not a golden rule. I give three valid solutions below.

If you're sure the block cannot be recursively included in itself, a simple cascade can be used:

.block--active {
    background-color: green;
}
.block--active .block__element-2,
.block--active .block__element-3 {
    font-weight: bold;
}

If the elements are directly located in the block, the children selector is valid:

.block--active {
    background-color: green;
}
.block--active > .block__element-2,
.block--active > .block__element-3 {
    font-weight: bold;
}

Or the flat solution (but not DRY):

.block--active {
    background-color: green;
}
.block__element-2--active,
.block__element-3--active {
    font-weight: bold;
}

With SCSS, there are several ways to write the first solution. Here is the one I use:

.block {
    &--active {
        background-color: green;
    }
    &--active &__element-2,
    &--active &__element-3 {
        font-weight: bold;
    }
}

See another solution here.


    CSS Howto..

    How to add background image to only one page in Jade

    How to get rid of the left and top margins in css when using html2pdf

    How may I stack multiple html/css buttons vertically along the center of the page?

    How can I edit CSS on an HTML tab?

    How to disable css warning “Unknown property” in Eclipse Mars?

    jquery/css: I want to change the bgcolor of row only after hovering for 1 or 2 seconds. How to achieve this?

    How to inline style an embedded gist with CSS

    How to put a table inside an inline-block element where cells have a percentage width

    Draggable elements in div show up behind drop zone when div is scrollable, need them to show in front

    How: have more than one CSS sprite on a page

    How do I give one stylesheet precedence over the other with Rails?

    How do I use CSS to keep multiple images relatively sized withing the same outer element?

    How to Change Font-family using JQuery's .css() function?

    how to overwrite RadWindow control CSS classes with mine?

    How can I fix the menu on the implanted header?

    how to bench a css pseudo-elements

    How to get value of input using Jquery and put it in css of an element

    how to show images with it's original smoothness in IE

    CSS: How to scale an image from the center instead of top-left

    How to make my SVG map render correctly in the browser?

    How to set CSS of one element depending on another element having a specific class?

    how to align vertically a dynamic-height div inside another fixed height div

    CSS: How to shadow a field like this? [closed]

    background-image: url(“images/plaid.jpg”) no-repeat; wont show up

    How to style the values in a textfield using CSS?

    How to validate HTML/CSS running in localhost?

    how to prevent css animation from running on page load

    How can I transition height: 0; to height: auto; using CSS?

    How to get the textarea to be same height as row

    How to assign a css class or id to smileys?